#
tokens: 59998/50000 1/2483 files (page 544/553)
lines: on (toggle) GitHub
raw markdown copy reset
This is page 544 of 553. Use http://codebase.md/awslabs/mcp?lines=true&page={x} to view the full context.

# Directory Structure

```
├── .devcontainer
│   └── devcontainer.json
├── .github
│   ├── actions
│   │   ├── build-and-push-container-image
│   │   │   └── action.yml
│   │   └── clear-space-ubuntu-latest-agressively
│   │       └── action.yml
│   ├── codecov.yml
│   ├── CODEOWNERS
│   ├── dependabot.yml
│   ├── ISSUE_TEMPLATE
│   │   ├── bug_report.yml
│   │   ├── documentation.yml
│   │   ├── feature_request.yml
│   │   ├── rfc.yml
│   │   └── support_awslabs_mcp_servers.yml
│   ├── pull_request_template.md
│   ├── SECURITY
│   ├── SUPPORT
│   └── workflows
│       ├── aws-api-mcp-upgrade-version.yml
│       ├── bandit-requirements.txt
│       ├── bandit.yml
│       ├── cfn_nag.yml
│       ├── check-gh-pages-builds.yml
│       ├── check-license-header-hash.txt
│       ├── check-license-header.json
│       ├── check-license-header.yml
│       ├── checkov.yml
│       ├── codeql.yml
│       ├── dependency-review-action.yml
│       ├── detect-secrets-requirements.txt
│       ├── gh-pages.yml
│       ├── merge-prevention.yml
│       ├── powershell.yml
│       ├── pre-commit-requirements.txt
│       ├── pre-commit.yml
│       ├── pull-request-lint.yml
│       ├── python.yml
│       ├── RELEASE_INSTRUCTIONS.md
│       ├── release-initiate-branch.yml
│       ├── release-merge-tag.yml
│       ├── release.py
│       ├── release.yml
│       ├── scanners.yml
│       ├── scorecard-analysis.yml
│       ├── semgrep-requirements.txt
│       ├── semgrep.yml
│       ├── stale.yml
│       ├── trivy.yml
│       └── typescript.yml
├── .gitignore
├── .pre-commit-config.yaml
├── .python-version
├── .ruff.toml
├── .secrets.baseline
├── CODE_OF_CONDUCT.md
├── CONTRIBUTING.md
├── DESIGN_GUIDELINES.md
├── DEVELOPER_GUIDE.md
├── docs
│   └── images
│       └── root-readme
│           ├── cline-api-provider-filled.png
│           ├── cline-chat-interface.png
│           ├── cline-custom-instructions.png
│           ├── cline-select-aws-profile.png
│           ├── cline-select-bedrock.png
│           ├── configure-mcp-servers.png
│           ├── install-cline-extension.png
│           ├── mcp-servers-installed.png
│           └── select-mcp-servers.png
├── docusaurus
│   ├── .gitignore
│   ├── docs
│   │   ├── installation.md
│   │   ├── intro.md
│   │   ├── samples
│   │   │   ├── index.md
│   │   │   ├── mcp-integration-with-kb.md
│   │   │   ├── mcp-integration-with-nova-canvas.md
│   │   │   └── stepfunctions-tool-mcp-server.md
│   │   ├── servers
│   │   │   ├── amazon-bedrock-agentcore-mcp-server.md
│   │   │   ├── amazon-keyspaces-mcp-server.md
│   │   │   ├── amazon-mq-mcp-server.md
│   │   │   ├── amazon-neptune-mcp-server.md
│   │   │   ├── amazon-qbusiness-anonymous-mcp-server.md
│   │   │   ├── amazon-qindex-mcp-server.md
│   │   │   ├── amazon-sns-sqs-mcp-server.md
│   │   │   ├── aurora-dsql-mcp-server.md
│   │   │   ├── aws-api-mcp-server.md
│   │   │   ├── aws-appsync-mcp-server.md
│   │   │   ├── aws-bedrock-custom-model-import-mcp-server.md
│   │   │   ├── aws-bedrock-data-automation-mcp-server.md
│   │   │   ├── aws-dataprocessing-mcp-server.md
│   │   │   ├── aws-diagram-mcp-server.md
│   │   │   ├── aws-documentation-mcp-server.md
│   │   │   ├── aws-healthomics-mcp-server.md
│   │   │   ├── aws-iot-sitewise-mcp-server.md
│   │   │   ├── aws-knowledge-mcp-server.md
│   │   │   ├── aws-location-mcp-server.md
│   │   │   ├── aws-msk-mcp-server.md
│   │   │   ├── aws-pricing-mcp-server.md
│   │   │   ├── aws-serverless-mcp-server.md
│   │   │   ├── aws-support-mcp-server.md
│   │   │   ├── bedrock-kb-retrieval-mcp-server.md
│   │   │   ├── billing-cost-management-mcp-server.md
│   │   │   ├── ccapi-mcp-server.md
│   │   │   ├── cdk-mcp-server.md
│   │   │   ├── cfn-mcp-server.md
│   │   │   ├── cloudtrail-mcp-server.md
│   │   │   ├── cloudwatch-appsignals-mcp-server.md
│   │   │   ├── cloudwatch-mcp-server.md
│   │   │   ├── code-doc-gen-mcp-server.md
│   │   │   ├── core-mcp-server.md
│   │   │   ├── cost-explorer-mcp-server.md
│   │   │   ├── documentdb-mcp-server.md
│   │   │   ├── dynamodb-mcp-server.md
│   │   │   ├── ecs-mcp-server.md
│   │   │   ├── eks-mcp-server.md
│   │   │   ├── elasticache-mcp-server.md
│   │   │   ├── finch-mcp-server.md
│   │   │   ├── frontend-mcp-server.md
│   │   │   ├── git-repo-research-mcp-server.md
│   │   │   ├── healthlake-mcp-server.md
│   │   │   ├── iam-mcp-server.md
│   │   │   ├── kendra-index-mcp-server.md
│   │   │   ├── lambda-tool-mcp-server.md
│   │   │   ├── memcached-mcp-server.md
│   │   │   ├── mysql-mcp-server.md
│   │   │   ├── nova-canvas-mcp-server.md
│   │   │   ├── openapi-mcp-server.md
│   │   │   ├── postgres-mcp-server.md
│   │   │   ├── prometheus-mcp-server.md
│   │   │   ├── redshift-mcp-server.md
│   │   │   ├── s3-tables-mcp-server.md
│   │   │   ├── stepfunctions-tool-mcp-server.md
│   │   │   ├── syntheticdata-mcp-server.md
│   │   │   ├── terraform-mcp-server.md
│   │   │   ├── timestream-for-influxdb-mcp-server.md
│   │   │   ├── valkey-mcp-server.md
│   │   │   └── well-architected-security-mcp-server.mdx
│   │   └── vibe_coding.md
│   ├── docusaurus.config.ts
│   ├── package-lock.json
│   ├── package.json
│   ├── README.md
│   ├── sidebars.ts
│   ├── src
│   │   ├── components
│   │   │   ├── HomepageFeatures
│   │   │   │   └── styles.module.css
│   │   │   └── ServerCards
│   │   │       ├── index.tsx
│   │   │       └── styles.module.css
│   │   ├── css
│   │   │   ├── custom.css
│   │   │   └── doc-override.css
│   │   └── pages
│   │       ├── index.module.css
│   │       └── servers.tsx
│   ├── static
│   │   ├── .nojekyll
│   │   ├── assets
│   │   │   ├── icons
│   │   │   │   ├── activity.svg
│   │   │   │   ├── book-open.svg
│   │   │   │   ├── cpu.svg
│   │   │   │   ├── database.svg
│   │   │   │   ├── dollar-sign.svg
│   │   │   │   ├── help-circle.svg
│   │   │   │   ├── key.svg
│   │   │   │   ├── server.svg
│   │   │   │   ├── share-2.svg
│   │   │   │   ├── tool.svg
│   │   │   │   └── zap.svg
│   │   │   └── server-cards.json
│   │   └── img
│   │       ├── aws-logo.svg
│   │       └── logo.png
│   └── tsconfig.json
├── LICENSE
├── NOTICE
├── README.md
├── samples
│   ├── mcp-integration-with-kb
│   │   ├── .env.example
│   │   ├── .python-version
│   │   ├── assets
│   │   │   └── simplified-mcp-flow-diagram.png
│   │   ├── clients
│   │   │   └── client_server.py
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── user_interfaces
│   │   │   └── chat_bedrock_st.py
│   │   └── uv.lock
│   ├── mcp-integration-with-nova-canvas
│   │   ├── .env.example
│   │   ├── .python-version
│   │   ├── clients
│   │   │   └── client_server.py
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── user_interfaces
│   │   │   └── image_generator_st.py
│   │   └── uv.lock
│   ├── README.md
│   └── stepfunctions-tool-mcp-server
│       ├── README.md
│       └── sample_state_machines
│           ├── customer-create
│           │   └── app.py
│           ├── customer-id-from-email
│           │   └── app.py
│           ├── customer-info-from-id
│           │   └── app.py
│           └── template.yml
├── scripts
│   ├── README.md
│   └── verify_package_name.py
├── src
│   ├── amazon-bedrock-agentcore-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── amazon_bedrock_agentcore_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── config.py
│   │   │       ├── server.py
│   │   │       └── utils
│   │   │           ├── __init__.py
│   │   │           ├── cache.py
│   │   │           ├── doc_fetcher.py
│   │   │           ├── indexer.py
│   │   │           ├── text_processor.py
│   │   │           └── url_validator.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── SECURITY.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── test_cache.py
│   │   │   ├── test_config.py
│   │   │   ├── test_doc_fetcher.py
│   │   │   ├── test_indexer.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   ├── test_server.py
│   │   │   ├── test_text_processor.py
│   │   │   └── test_url_validator.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── amazon-kendra-index-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── amazon_kendra_index_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── server.py
│   │   │       └── util.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── amazon-keyspaces-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── amazon_keyspaces_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── client.py
│   │   │       ├── config.py
│   │   │       ├── consts.py
│   │   │       ├── llm_context.py
│   │   │       ├── models.py
│   │   │       ├── server.py
│   │   │       └── services.py
│   │   ├── CHANGELOG.md
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── run_tests.sh
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── test_client.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   ├── test_query_analysis_service.py
│   │   │   ├── test_server.py
│   │   │   └── test_services.py
│   │   └── uv.lock
│   ├── amazon-mq-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── amazon_mq_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── aws_service_mcp_generator.py
│   │   │       ├── consts.py
│   │   │       ├── rabbitmq
│   │   │       │   ├── __init__.py
│   │   │       │   ├── admin.py
│   │   │       │   ├── connection.py
│   │   │       │   ├── doc
│   │   │       │   │   ├── rabbitmq_broker_sizing_guide.md
│   │   │       │   │   ├── rabbitmq_performance_optimization_best_practice.md
│   │   │       │   │   ├── rabbitmq_production_deployment_guidelines.md
│   │   │       │   │   ├── rabbitmq_quorum_queue_migration_guide.md
│   │   │       │   │   └── rabbitmq_setup_best_practice.md
│   │   │       │   ├── handlers.py
│   │   │       │   └── module.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── example
│   │   │   └── sample_mcp_q_cli.json
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── .gitignore
│   │   │   ├── rabbitmq
│   │   │   │   ├── __init__.py
│   │   │   │   ├── conftest.py
│   │   │   │   ├── test_admin.py
│   │   │   │   ├── test_connection.py
│   │   │   │   ├── test_handlers.py
│   │   │   │   └── test_module.py
│   │   │   ├── test_aws_service_mcp_generator.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── amazon-neptune-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── amazon_neptune_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── exceptions.py
│   │   │       ├── graph_store
│   │   │       │   ├── __init__.py
│   │   │       │   ├── analytics.py
│   │   │       │   ├── base.py
│   │   │       │   └── database.py
│   │   │       ├── models.py
│   │   │       ├── neptune.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── test_analytics.py
│   │   │   ├── test_database.py
│   │   │   ├── test_exceptions.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   ├── test_models.py
│   │   │   ├── test_neptune.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── amazon-qbusiness-anonymous-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── amazon_qbusiness_anonymous_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── clients.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── amazon-qindex-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── amazon_qindex_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── clients.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── test_clients.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   └── test_server.py
│   │   └── uv.lock
│   ├── amazon-sns-sqs-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── amazon_sns_sqs_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── common.py
│   │   │       ├── consts.py
│   │   │       ├── generator.py
│   │   │       ├── server.py
│   │   │       ├── sns.py
│   │   │       └── sqs.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── print_tools.py
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── run_tests.sh
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── .gitignore
│   │   │   ├── README.md
│   │   │   ├── test_common.py
│   │   │   ├── test_generator.py
│   │   │   ├── test_server.py
│   │   │   ├── test_sns.py
│   │   │   └── test_sqs.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── aurora-dsql-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── aurora_dsql_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── consts.py
│   │   │       ├── mutable_sql_detector.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── test_connection_reuse.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   ├── test_profile_option.py
│   │   │   ├── test_readonly_enforcement.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── aws-api-mcp-server
│   │   ├── .gitattributes
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── aws_api_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── core
│   │   │       │   ├── __init__.py
│   │   │       │   ├── agent_scripts
│   │   │       │   │   ├── __init__.py
│   │   │       │   │   ├── manager.py
│   │   │       │   │   ├── models.py
│   │   │       │   │   └── registry
│   │   │       │   │       ├── __init__.py
│   │   │       │   │       ├── application-failure-troubleshooting.script.md
│   │   │       │   │       ├── cloudtral-mutli-region-setup.script.md
│   │   │       │   │       ├── create_amazon_aurora_db_cluster_with_instances.script.md
│   │   │       │   │       ├── lambda-timeout-debugging.script.md
│   │   │       │   │       ├── scripts_format.md
│   │   │       │   │       └── troubleshoot-permissions-with-cloudtrail-events.script.md
│   │   │       │   ├── aws
│   │   │       │   │   ├── __init__.py
│   │   │       │   │   ├── driver.py
│   │   │       │   │   ├── pagination.py
│   │   │       │   │   ├── regions.py
│   │   │       │   │   ├── service.py
│   │   │       │   │   └── services.py
│   │   │       │   ├── common
│   │   │       │   │   ├── __init__.py
│   │   │       │   │   ├── command_metadata.py
│   │   │       │   │   ├── command.py
│   │   │       │   │   ├── config.py
│   │   │       │   │   ├── errors.py
│   │   │       │   │   ├── file_operations.py
│   │   │       │   │   ├── file_system_controls.py
│   │   │       │   │   ├── helpers.py
│   │   │       │   │   ├── models.py
│   │   │       │   │   └── py.typed
│   │   │       │   ├── data
│   │   │       │   │   └── api_metadata.json
│   │   │       │   ├── metadata
│   │   │       │   │   ├── __init__.py
│   │   │       │   │   └── read_only_operations_list.py
│   │   │       │   ├── parser
│   │   │       │   │   ├── __init__.py
│   │   │       │   │   ├── custom_validators
│   │   │       │   │   │   ├── __init__.py
│   │   │       │   │   │   ├── botocore_param_validator.py
│   │   │       │   │   │   ├── ec2_validator.py
│   │   │       │   │   │   └── ssm_validator.py
│   │   │       │   │   ├── interpretation.py
│   │   │       │   │   ├── lexer.py
│   │   │       │   │   └── parser.py
│   │   │       │   ├── py.typed
│   │   │       │   └── security
│   │   │       │       ├── __init__.py
│   │   │       │       ├── aws_api_customization.json
│   │   │       │       └── policy.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── CONTRIBUTING.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── agent_scripts
│   │   │   │   ├── __init__.py
│   │   │   │   ├── test_manager.py
│   │   │   │   └── test_registry
│   │   │   │       ├── another_valid_script.script.md
│   │   │   │       ├── test_script.script.md
│   │   │   │       └── valid_script.script.md
│   │   │   ├── aws
│   │   │   │   ├── __init__.py
│   │   │   │   ├── test_driver.py
│   │   │   │   ├── test_pagination.py
│   │   │   │   ├── test_service.py
│   │   │   │   └── test_services.py
│   │   │   ├── common
│   │   │   │   ├── test_command.py
│   │   │   │   ├── test_config.py
│   │   │   │   ├── test_file_operations.py
│   │   │   │   ├── test_file_system_controls.py
│   │   │   │   ├── test_file_validation.py
│   │   │   │   └── test_helpers.py
│   │   │   ├── fixtures.py
│   │   │   ├── history_handler.py
│   │   │   ├── metadata
│   │   │   │   ├── __init__.py
│   │   │   │   └── test_read_only_operations_list.py
│   │   │   ├── parser
│   │   │   │   ├── __init__.py
│   │   │   │   ├── test_file_path_detection.py
│   │   │   │   ├── test_lexer.py
│   │   │   │   ├── test_parser_customizations.py
│   │   │   │   └── test_parser.py
│   │   │   ├── test_security_policy.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── aws-appsync-mcp-server
│   │   ├── .dockerignore
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── aws_appsync_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── decorators.py
│   │   │       ├── helpers.py
│   │   │       ├── operations
│   │   │       │   ├── __init__.py
│   │   │       │   ├── create_api_cache.py
│   │   │       │   ├── create_api_key.py
│   │   │       │   ├── create_api.py
│   │   │       │   ├── create_channel_namespace.py
│   │   │       │   ├── create_datasource.py
│   │   │       │   ├── create_domain_name.py
│   │   │       │   ├── create_function.py
│   │   │       │   ├── create_graphql_api.py
│   │   │       │   ├── create_resolver.py
│   │   │       │   └── create_schema.py
│   │   │       ├── server.py
│   │   │       ├── tools
│   │   │       │   ├── __init__.py
│   │   │       │   ├── create_api_cache.py
│   │   │       │   ├── create_api_key.py
│   │   │       │   ├── create_api.py
│   │   │       │   ├── create_channel_namespace.py
│   │   │       │   ├── create_datasource.py
│   │   │       │   ├── create_domain_name.py
│   │   │       │   ├── create_function.py
│   │   │       │   ├── create_graphql_api.py
│   │   │       │   ├── create_resolver.py
│   │   │       │   └── create_schema.py
│   │   │       └── validators.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── test_all_create_tools_write_protection.py
│   │   │   ├── test_create_api_cache.py
│   │   │   ├── test_create_api_key.py
│   │   │   ├── test_create_api.py
│   │   │   ├── test_create_channel_namespace.py
│   │   │   ├── test_create_datasource_tool.py
│   │   │   ├── test_create_datasource.py
│   │   │   ├── test_create_domain_name.py
│   │   │   ├── test_create_function.py
│   │   │   ├── test_create_graphql_api.py
│   │   │   ├── test_create_resolver.py
│   │   │   ├── test_create_schema_tool.py
│   │   │   ├── test_create_schema.py
│   │   │   ├── test_helpers.py
│   │   │   ├── test_server.py
│   │   │   ├── test_validators.py
│   │   │   └── test_write_operation.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── aws-bedrock-custom-model-import-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── aws_bedrock_custom_model_import_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── client.py
│   │   │       ├── llm_context.py
│   │   │       ├── models.py
│   │   │       ├── prompts.py
│   │   │       ├── server.py
│   │   │       ├── services
│   │   │       │   ├── __init__.py
│   │   │       │   ├── imported_model_service.py
│   │   │       │   └── model_import_service.py
│   │   │       ├── tools
│   │   │       │   ├── create_model_import_job.py
│   │   │       │   ├── delete_imported_model.py
│   │   │       │   ├── get_imported_model.py
│   │   │       │   ├── get_model_import_job.py
│   │   │       │   ├── list_imported_models.py
│   │   │       │   └── list_model_import_jobs.py
│   │   │       └── utils
│   │   │           ├── __init__.py
│   │   │           ├── aws.py
│   │   │           ├── config.py
│   │   │           ├── consts.py
│   │   │           └── matching.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── services
│   │   │   │   ├── test_imported_model_service.py
│   │   │   │   └── test_model_import_service.py
│   │   │   ├── test_client.py
│   │   │   ├── test_init.py
│   │   │   ├── test_llm_context.py
│   │   │   ├── test_prompts.py
│   │   │   ├── test_server.py
│   │   │   ├── tools
│   │   │   │   ├── test_create_model_import_job.py
│   │   │   │   ├── test_delete_imported_model.py
│   │   │   │   ├── test_get_imported_model.py
│   │   │   │   ├── test_get_model_import_job.py
│   │   │   │   ├── test_list_imported_models.py
│   │   │   │   └── test_list_model_import_jobs.py
│   │   │   └── utils
│   │   │       ├── test_aws.py
│   │   │       ├── test_config.py
│   │   │       └── test_matching.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── aws-bedrock-data-automation-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── aws_bedrock_data_automation_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── helpers.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── test_helpers.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── aws-dataprocessing-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── aws_dataprocessing_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── core
│   │   │       │   ├── __init__.py
│   │   │       │   └── glue_data_catalog
│   │   │       │       ├── __init__.py
│   │   │       │       ├── data_catalog_database_manager.py
│   │   │       │       ├── data_catalog_handler.py
│   │   │       │       └── data_catalog_table_manager.py
│   │   │       ├── handlers
│   │   │       │   ├── __init__.py
│   │   │       │   ├── athena
│   │   │       │   │   ├── __init__.py
│   │   │       │   │   ├── athena_data_catalog_handler.py
│   │   │       │   │   ├── athena_query_handler.py
│   │   │       │   │   └── athena_workgroup_handler.py
│   │   │       │   ├── commons
│   │   │       │   │   ├── __init__.py
│   │   │       │   │   └── common_resource_handler.py
│   │   │       │   ├── emr
│   │   │       │   │   ├── emr_ec2_cluster_handler.py
│   │   │       │   │   ├── emr_ec2_instance_handler.py
│   │   │       │   │   └── emr_ec2_steps_handler.py
│   │   │       │   └── glue
│   │   │       │       ├── __init__.py
│   │   │       │       ├── crawler_handler.py
│   │   │       │       ├── data_catalog_handler.py
│   │   │       │       ├── glue_commons_handler.py
│   │   │       │       ├── glue_etl_handler.py
│   │   │       │       ├── interactive_sessions_handler.py
│   │   │       │       └── worklows_handler.py
│   │   │       ├── models
│   │   │       │   ├── __init__.py
│   │   │       │   ├── athena_models.py
│   │   │       │   ├── common_resource_models.py
│   │   │       │   ├── data_catalog_models.py
│   │   │       │   ├── emr_models.py
│   │   │       │   └── glue_models.py
│   │   │       ├── server.py
│   │   │       └── utils
│   │   │           ├── __init__.py
│   │   │           ├── aws_helper.py
│   │   │           ├── consts.py
│   │   │           ├── logging_helper.py
│   │   │           └── sql_analyzer.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── core
│   │   │   │   ├── __init__.py
│   │   │   │   └── glue_data_catalog
│   │   │   │       ├── __init__.py
│   │   │   │       ├── test_data_catalog_database_manager.py
│   │   │   │       ├── test_data_catalog_handler.py
│   │   │   │       └── test_data_catalog_table_manager.py
│   │   │   ├── handlers
│   │   │   │   ├── __init__.py
│   │   │   │   ├── athena
│   │   │   │   │   ├── __init__.py
│   │   │   │   │   ├── test_athena_data_catalog_handler.py
│   │   │   │   │   ├── test_athena_query_handler.py
│   │   │   │   │   ├── test_athena_workgroup_handler.py
│   │   │   │   │   └── test_custom_tags_athena.py
│   │   │   │   ├── commons
│   │   │   │   │   ├── __init__.py
│   │   │   │   │   └── test_common_resource_handler.py
│   │   │   │   ├── emr
│   │   │   │   │   ├── __init__.py
│   │   │   │   │   ├── test_custom_tags_emr.py
│   │   │   │   │   ├── test_emr_ec2_cluster_handler.py
│   │   │   │   │   ├── test_emr_ec2_instance_handler.py
│   │   │   │   │   └── test_emr_ec2_steps_handler.py
│   │   │   │   └── glue
│   │   │   │       ├── __init__.py
│   │   │   │       ├── test_crawler_handler.py
│   │   │   │       ├── test_custom_tags_glue.py
│   │   │   │       ├── test_data_catalog_handler.py
│   │   │   │       ├── test_glue_commons_handler.py
│   │   │   │       ├── test_glue_etl_handler.py
│   │   │   │       ├── test_glue_interactive_sessions_handler.py
│   │   │   │       └── test_glue_workflows_handler.py
│   │   │   ├── models
│   │   │   │   ├── __init__.py
│   │   │   │   ├── test_athena_models.py
│   │   │   │   ├── test_common_resource_models.py
│   │   │   │   ├── test_data_catalog_models.py
│   │   │   │   ├── test_emr_models.py
│   │   │   │   ├── test_glue_models.py
│   │   │   │   ├── test_interactive_sessions_models.py
│   │   │   │   └── test_workflows_models.py
│   │   │   ├── test_init.py
│   │   │   ├── test_server.py
│   │   │   └── utils
│   │   │       ├── __init__.py
│   │   │       ├── test_aws_helper.py
│   │   │       ├── test_custom_tags.py
│   │   │       ├── test_logging_helper.py
│   │   │       └── test_sql_analyzer.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── aws-diagram-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── aws_diagram_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── diagrams_tools.py
│   │   │       ├── models.py
│   │   │       ├── scanner.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── .gitignore
│   │   │   ├── conftest.py
│   │   │   ├── README.md
│   │   │   ├── resources
│   │   │   │   ├── __init__.py
│   │   │   │   └── example_diagrams
│   │   │   │       ├── __init__.py
│   │   │   │       ├── aws_example.py
│   │   │   │       ├── flow_example.py
│   │   │   │       └── sequence_example.py
│   │   │   ├── test_diagrams.py
│   │   │   ├── test_models.py
│   │   │   ├── test_sarif_fix.py
│   │   │   ├── test_scanner.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── aws-documentation-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── aws_documentation_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── models.py
│   │   │       ├── server_aws_cn.py
│   │   │       ├── server_aws.py
│   │   │       ├── server_utils.py
│   │   │       ├── server.py
│   │   │       └── util.py
│   │   ├── basic-usage.gif
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── constants.py
│   │   │   ├── resources
│   │   │   │   └── lambda_sns_raw.html
│   │   │   ├── test_aws_cn_get_available_services_live.py
│   │   │   ├── test_aws_cn_read_documentation_live.py
│   │   │   ├── test_aws_read_documentation_live.py
│   │   │   ├── test_aws_recommend_live.py
│   │   │   ├── test_aws_search_live.py
│   │   │   ├── test_metadata_handling.py
│   │   │   ├── test_models.py
│   │   │   ├── test_server_aws_cn.py
│   │   │   ├── test_server_aws.py
│   │   │   ├── test_server_utils.py
│   │   │   ├── test_server.py
│   │   │   └── test_util.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── aws-healthomics-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── aws_healthomics_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── consts.py
│   │   │       ├── models.py
│   │   │       ├── server.py
│   │   │       ├── tools
│   │   │       │   ├── __init__.py
│   │   │       │   ├── helper_tools.py
│   │   │       │   ├── run_analysis.py
│   │   │       │   ├── troubleshooting.py
│   │   │       │   ├── workflow_analysis.py
│   │   │       │   ├── workflow_execution.py
│   │   │       │   ├── workflow_linting.py
│   │   │       │   └── workflow_management.py
│   │   │       └── utils
│   │   │           ├── __init__.py
│   │   │           ├── aws_utils.py
│   │   │           ├── s3_utils.py
│   │   │           └── validation_utils.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── docs
│   │   │   └── workflow_linting.md
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── conftest.py
│   │   │   ├── test_aws_utils.py
│   │   │   ├── test_consts.py
│   │   │   ├── test_helper_tools.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   ├── test_models.py
│   │   │   ├── test_run_analysis.py
│   │   │   ├── test_s3_utils.py
│   │   │   ├── test_server.py
│   │   │   ├── test_troubleshooting.py
│   │   │   ├── test_workflow_analysis.py
│   │   │   ├── test_workflow_execution.py
│   │   │   ├── test_workflow_linting.py
│   │   │   ├── test_workflow_management.py
│   │   │   └── test_workflow_tools.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── aws-iot-sitewise-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── aws_iot_sitewise_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── client.py
│   │   │       ├── models.py
│   │   │       ├── prompts
│   │   │       │   ├── __init__.py
│   │   │       │   ├── asset_hierarchy.py
│   │   │       │   ├── bulk_import_workflow.py
│   │   │       │   ├── data_exploration.py
│   │   │       │   └── data_ingestion.py
│   │   │       ├── server.py
│   │   │       ├── tool_metadata.py
│   │   │       ├── tools
│   │   │       │   ├── __init__.py
│   │   │       │   ├── sitewise_access.py
│   │   │       │   ├── sitewise_asset_models.py
│   │   │       │   ├── sitewise_assets.py
│   │   │       │   ├── sitewise_data.py
│   │   │       │   ├── sitewise_gateways.py
│   │   │       │   └── sitewise_metadata_transfer.py
│   │   │       └── validation.py
│   │   ├── CHANGELOG.md
│   │   ├── DEVELOPMENT.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── examples
│   │   │   └── wind_farm_example.py
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── run_server.py
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── test_client.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   ├── test_models.py
│   │   │   ├── test_server.py
│   │   │   ├── test_sitewise_access.py
│   │   │   ├── test_sitewise_asset_models.py
│   │   │   ├── test_sitewise_assets.py
│   │   │   ├── test_sitewise_data.py
│   │   │   ├── test_sitewise_gateways.py
│   │   │   ├── test_sitewise_metadata_transfer.py
│   │   │   └── test_validation.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── aws-knowledge-mcp-server
│   │   └── README.md
│   ├── aws-location-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── aws_location_server
│   │   │       ├── __init__.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── test_server_integration.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── aws-msk-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── aws_msk_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── server.py
│   │   │       └── tools
│   │   │           ├── __init__.py
│   │   │           ├── common_functions
│   │   │           │   ├── __init__.py
│   │   │           │   ├── client_manager.py
│   │   │           │   └── common_functions.py
│   │   │           ├── logs_and_telemetry
│   │   │           │   ├── __init__.py
│   │   │           │   ├── cluster_metrics_tools.py
│   │   │           │   ├── list_customer_iam_access.py
│   │   │           │   └── metric_config.py
│   │   │           ├── mutate_cluster
│   │   │           │   ├── __init__.py
│   │   │           │   ├── batch_associate_scram_secret.py
│   │   │           │   ├── batch_disassociate_scram_secret.py
│   │   │           │   ├── create_cluster_v2.py
│   │   │           │   ├── put_cluster_policy.py
│   │   │           │   ├── reboot_broker.py
│   │   │           │   ├── update_broker_count.py
│   │   │           │   ├── update_broker_storage.py
│   │   │           │   ├── update_broker_type.py
│   │   │           │   ├── update_cluster_configuration.py
│   │   │           │   ├── update_monitoring.py
│   │   │           │   └── update_security.py
│   │   │           ├── mutate_config
│   │   │           │   ├── __init__.py
│   │   │           │   ├── create_configuration.py
│   │   │           │   ├── tag_resource.py
│   │   │           │   ├── untag_resource.py
│   │   │           │   └── update_configuration.py
│   │   │           ├── mutate_vpc
│   │   │           │   ├── __init__.py
│   │   │           │   ├── create_vpc_connection.py
│   │   │           │   ├── delete_vpc_connection.py
│   │   │           │   └── reject_client_vpc_connection.py
│   │   │           ├── read_cluster
│   │   │           │   ├── __init__.py
│   │   │           │   ├── describe_cluster_operation.py
│   │   │           │   ├── describe_cluster.py
│   │   │           │   ├── get_bootstrap_brokers.py
│   │   │           │   ├── get_cluster_policy.py
│   │   │           │   ├── get_compatible_kafka_versions.py
│   │   │           │   ├── list_client_vpc_connections.py
│   │   │           │   ├── list_cluster_operations.py
│   │   │           │   ├── list_nodes.py
│   │   │           │   └── list_scram_secrets.py
│   │   │           ├── read_config
│   │   │           │   ├── __init__.py
│   │   │           │   ├── describe_configuration_revision.py
│   │   │           │   ├── describe_configuration.py
│   │   │           │   ├── list_configuration_revisions.py
│   │   │           │   └── list_tags_for_resource.py
│   │   │           ├── read_global
│   │   │           │   ├── __init__.py
│   │   │           │   ├── list_clusters.py
│   │   │           │   ├── list_configurations.py
│   │   │           │   ├── list_kafka_versions.py
│   │   │           │   └── list_vpc_connections.py
│   │   │           ├── read_vpc
│   │   │           │   ├── __init__.py
│   │   │           │   └── describe_vpc_connection.py
│   │   │           └── static_tools
│   │   │               ├── __init__.py
│   │   │               └── cluster_best_practices.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── test_client_manager.py
│   │   │   ├── test_cluster_metrics_tools.py
│   │   │   ├── test_common_functions.py
│   │   │   ├── test_create_cluster_v2.py
│   │   │   ├── test_create_configuration.py
│   │   │   ├── test_create_vpc_connection.py
│   │   │   ├── test_delete_vpc_connection.py
│   │   │   ├── test_describe_cluster_operation.py
│   │   │   ├── test_describe_cluster.py
│   │   │   ├── test_describe_configuration_revision.py
│   │   │   ├── test_describe_configuration.py
│   │   │   ├── test_describe_vpc_connection.py
│   │   │   ├── test_get_bootstrap_brokers.py
│   │   │   ├── test_get_cluster_policy.py
│   │   │   ├── test_get_compatible_kafka_versions.py
│   │   │   ├── test_init.py
│   │   │   ├── test_list_client_vpc_connections.py
│   │   │   ├── test_list_cluster_operations.py
│   │   │   ├── test_list_clusters.py
│   │   │   ├── test_list_configuration_revisions.py
│   │   │   ├── test_list_configurations.py
│   │   │   ├── test_list_customer_iam_access.py
│   │   │   ├── test_list_kafka_versions.py
│   │   │   ├── test_list_nodes.py
│   │   │   ├── test_list_scram_secrets.py
│   │   │   ├── test_list_tags_for_resource.py
│   │   │   ├── test_list_vpc_connections.py
│   │   │   ├── test_logs_and_telemetry.py
│   │   │   ├── test_main.py
│   │   │   ├── test_mutate_cluster_init.py
│   │   │   ├── test_mutate_cluster_success_cases.py
│   │   │   ├── test_mutate_cluster.py
│   │   │   ├── test_mutate_config_init.py
│   │   │   ├── test_mutate_vpc_init.py
│   │   │   ├── test_read_cluster_init_updated.py
│   │   │   ├── test_read_cluster_init.py
│   │   │   ├── test_read_config_init.py
│   │   │   ├── test_read_global_init.py
│   │   │   ├── test_read_vpc_init.py
│   │   │   ├── test_reject_client_vpc_connection.py
│   │   │   ├── test_server.py
│   │   │   ├── test_static_tools_init.py
│   │   │   ├── test_tag_resource.py
│   │   │   ├── test_tool_descriptions.py
│   │   │   ├── test_untag_resource.py
│   │   │   └── test_update_configuration.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── aws-pricing-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── aws_pricing_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── cdk_analyzer.py
│   │   │       ├── consts.py
│   │   │       ├── helpers.py
│   │   │       ├── models.py
│   │   │       ├── pricing_client.py
│   │   │       ├── pricing_transformer.py
│   │   │       ├── report_generator.py
│   │   │       ├── server.py
│   │   │       ├── static
│   │   │       │   ├── __init__.py
│   │   │       │   ├── COST_REPORT_TEMPLATE.md
│   │   │       │   └── patterns
│   │   │       │       ├── __init__.py
│   │   │       │       └── BEDROCK.md
│   │   │       └── terraform_analyzer.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── test_cdk_analyzer.py
│   │   │   ├── test_helpers.py
│   │   │   ├── test_pricing_client.py
│   │   │   ├── test_pricing_transformer.py
│   │   │   ├── test_report_generator.py
│   │   │   ├── test_server.py
│   │   │   └── test_terraform_analyzer.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── aws-serverless-mcp-server
│   │   ├── .pre-commit.config.yaml
│   │   ├── .python-version
│   │   ├── .secrets.baseline
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── aws_serverless_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── models.py
│   │   │       ├── resources
│   │   │       │   ├── __init__.py
│   │   │       │   ├── deployment_details.py
│   │   │       │   ├── deployment_list.py
│   │   │       │   ├── template_details.py
│   │   │       │   └── template_list.py
│   │   │       ├── server.py
│   │   │       ├── template
│   │   │       │   ├── __init__.py
│   │   │       │   ├── registry.py
│   │   │       │   ├── renderer.py
│   │   │       │   └── templates
│   │   │       │       ├── backend.j2
│   │   │       │       ├── frontend.j2
│   │   │       │       ├── fullstack.j2
│   │   │       │       └── README.md
│   │   │       ├── templates
│   │   │       │   ├── __init__.py
│   │   │       │   └── iam_policies.py
│   │   │       ├── tools
│   │   │       │   ├── common
│   │   │       │   │   └── base_tool.py
│   │   │       │   ├── esm
│   │   │       │   │   ├── __init__.py
│   │   │       │   │   ├── esm_diagnosis.py
│   │   │       │   │   ├── esm_guidance.py
│   │   │       │   │   ├── esm_recommend.py
│   │   │       │   │   └── secure_esm_guidance.py
│   │   │       │   ├── guidance
│   │   │       │   │   ├── __init__.py
│   │   │       │   │   ├── deploy_serverless_app_help.py
│   │   │       │   │   ├── get_iac_guidance.py
│   │   │       │   │   ├── get_lambda_event_schemas.py
│   │   │       │   │   ├── get_lambda_guidance.py
│   │   │       │   │   └── get_serverless_templates.py
│   │   │       │   ├── poller
│   │   │       │   │   ├── __init__.py
│   │   │       │   │   ├── esm_diagnosis.py
│   │   │       │   │   ├── esm_guidance.py
│   │   │       │   │   └── esm_recommend.py
│   │   │       │   ├── sam
│   │   │       │   │   ├── __init__.py
│   │   │       │   │   ├── sam_build.py
│   │   │       │   │   ├── sam_deploy.py
│   │   │       │   │   ├── sam_init.py
│   │   │       │   │   ├── sam_local_invoke.py
│   │   │       │   │   └── sam_logs.py
│   │   │       │   ├── schemas
│   │   │       │   │   ├── __init__.py
│   │   │       │   │   ├── describe_schema.py
│   │   │       │   │   ├── list_registries.py
│   │   │       │   │   └── search_schema.py
│   │   │       │   └── webapps
│   │   │       │       ├── __init__.py
│   │   │       │       ├── configure_domain.py
│   │   │       │       ├── deploy_webapp.py
│   │   │       │       ├── get_metrics.py
│   │   │       │       ├── update_webapp_frontend.py
│   │   │       │       ├── utils
│   │   │       │       │   ├── deploy_service.py
│   │   │       │       │   ├── frontend_uploader.py
│   │   │       │       │   └── startup_script_generator.py
│   │   │       │       └── webapp_deployment_help.py
│   │   │       └── utils
│   │   │           ├── __init__.py
│   │   │           ├── aws_client_helper.py
│   │   │           ├── cloudformation.py
│   │   │           ├── const.py
│   │   │           ├── data_scrubber.py
│   │   │           ├── deployment_manager.py
│   │   │           ├── github.py
│   │   │           └── process.py
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── README.md
│   │   │   ├── test_cloudformation.py
│   │   │   ├── test_configure_domain.py
│   │   │   ├── test_data_scrubber.py
│   │   │   ├── test_deploy_serverless_app_help.py
│   │   │   ├── test_deploy_service.py
│   │   │   ├── test_deploy_webapp.py
│   │   │   ├── test_deployment_details.py
│   │   │   ├── test_deployment_help.py
│   │   │   ├── test_deployment_list.py
│   │   │   ├── test_deployment_manager.py
│   │   │   ├── test_esm_diagnosis.py
│   │   │   ├── test_esm_guidance.py
│   │   │   ├── test_esm_recommend.py
│   │   │   ├── test_frontend_uploader.py
│   │   │   ├── test_get_iac_guidance.py
│   │   │   ├── test_get_lambda_event_schemas.py
│   │   │   ├── test_get_lambda_guidance.py
│   │   │   ├── test_get_metrics.py
│   │   │   ├── test_get_serverless_templates.py
│   │   │   ├── test_github.py
│   │   │   ├── test_iam_policies.py
│   │   │   ├── test_models.py
│   │   │   ├── test_process.py
│   │   │   ├── test_sam_build.py
│   │   │   ├── test_sam_deploy.py
│   │   │   ├── test_sam_init.py
│   │   │   ├── test_sam_local_invoke.py
│   │   │   ├── test_sam_logs.py
│   │   │   ├── test_schemas.py
│   │   │   ├── test_secure_esm_guidance.py
│   │   │   ├── test_server.py
│   │   │   ├── test_startup_script_generator.py
│   │   │   ├── test_template_details.py
│   │   │   ├── test_template_list.py
│   │   │   ├── test_template_registry.py
│   │   │   ├── test_template_renderer.py
│   │   │   └── test_update_webapp_frontend.py
│   │   └── uv.lock
│   ├── aws-support-mcp-server
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── aws_support_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── client.py
│   │   │       ├── consts.py
│   │   │       ├── debug_helper.py
│   │   │       ├── errors.py
│   │   │       ├── formatters.py
│   │   │       ├── models.py
│   │   │       └── server.py
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftests.py
│   │   │   ├── test_aws_support_mcp_server.py
│   │   │   └── test_models.py
│   │   └── uv.lock
│   ├── bedrock-kb-retrieval-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── bedrock_kb_retrieval_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── knowledgebases
│   │   │       │   ├── __init__.py
│   │   │       │   ├── clients.py
│   │   │       │   ├── discovery.py
│   │   │       │   └── retrieval.py
│   │   │       ├── models.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── run_tests.sh
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── .gitignore
│   │   │   ├── conftest.py
│   │   │   ├── README.md
│   │   │   ├── test_clients.py
│   │   │   ├── test_discovery.py
│   │   │   ├── test_env_config.py
│   │   │   ├── test_models.py
│   │   │   ├── test_retrieval.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── billing-cost-management-mcp-server
│   │   ├── __init__.py
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── billing_cost_management_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── models.py
│   │   │       ├── prompts
│   │   │       │   ├── __init__.py
│   │   │       │   ├── decorator.py
│   │   │       │   ├── graviton_migration.py
│   │   │       │   ├── README.md
│   │   │       │   ├── savings_plans.py
│   │   │       │   └── types.py
│   │   │       ├── server.py
│   │   │       ├── templates
│   │   │       │   └── recommendation_templates
│   │   │       │       ├── ebs_volume.template
│   │   │       │       ├── ec2_asg.template
│   │   │       │       ├── ec2_instance.template
│   │   │       │       ├── ecs_service.template
│   │   │       │       ├── idle.template
│   │   │       │       ├── lambda_function.template
│   │   │       │       ├── rds_database.template
│   │   │       │       ├── reserved_instances.template
│   │   │       │       └── savings_plans.template
│   │   │       ├── tools
│   │   │       │   ├── __init__.py
│   │   │       │   ├── aws_pricing_operations.py
│   │   │       │   ├── aws_pricing_tools.py
│   │   │       │   ├── bcm_pricing_calculator_tools.py
│   │   │       │   ├── budget_tools.py
│   │   │       │   ├── compute_optimizer_tools.py
│   │   │       │   ├── cost_anomaly_tools.py
│   │   │       │   ├── cost_comparison_tools.py
│   │   │       │   ├── cost_explorer_operations.py
│   │   │       │   ├── cost_explorer_tools.py
│   │   │       │   ├── cost_optimization_hub_helpers.py
│   │   │       │   ├── cost_optimization_hub_tools.py
│   │   │       │   ├── free_tier_usage_tools.py
│   │   │       │   ├── recommendation_details_tools.py
│   │   │       │   ├── ri_performance_tools.py
│   │   │       │   ├── sp_performance_tools.py
│   │   │       │   ├── storage_lens_tools.py
│   │   │       │   └── unified_sql_tools.py
│   │   │       └── utilities
│   │   │           ├── __init__.py
│   │   │           ├── aws_service_base.py
│   │   │           ├── constants.py
│   │   │           ├── logging_utils.py
│   │   │           └── sql_utils.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── requirements.txt
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── prompts
│   │   │   │   ├── __init__.py
│   │   │   │   └── test_prompts.py
│   │   │   ├── README.md
│   │   │   ├── test_models.py
│   │   │   ├── test_server.py
│   │   │   ├── tools
│   │   │   │   ├── __init__.py
│   │   │   │   ├── fixtures.py
│   │   │   │   ├── test_aws_bcm_pricing_calculator_tools.py
│   │   │   │   ├── test_aws_pricing_tools.py
│   │   │   │   ├── test_budget_tools.py
│   │   │   │   ├── test_compute_optimizer_tools.py
│   │   │   │   ├── test_cost_anomaly_tools_enhanced.py
│   │   │   │   ├── test_cost_anomaly_tools.py
│   │   │   │   ├── test_cost_comparison_tools.py
│   │   │   │   ├── test_cost_explorer_operations.py
│   │   │   │   ├── test_cost_explorer_tools.py
│   │   │   │   ├── test_cost_optimization_hub_helpers.py
│   │   │   │   ├── test_cost_optimization_hub_tools.py
│   │   │   │   ├── test_free_tier_usage_tools_new.py
│   │   │   │   ├── test_recommendation_details_tools.py
│   │   │   │   ├── test_ri_performance_tools.py
│   │   │   │   ├── test_sp_performance_tools.py
│   │   │   │   ├── test_storage_lens_tools.py
│   │   │   │   └── test_unified_sql_tools.py
│   │   │   └── utilities
│   │   │       ├── test_aws_service_base.py
│   │   │       └── test_sql_utils.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── ccapi-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── ccapi_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── aws_client.py
│   │   │       ├── cloud_control_utils.py
│   │   │       ├── context.py
│   │   │       ├── errors.py
│   │   │       ├── iac_generator.py
│   │   │       ├── impl
│   │   │       │   ├── __init__.py
│   │   │       │   ├── tools
│   │   │       │   │   ├── __init__.py
│   │   │       │   │   ├── explanation.py
│   │   │       │   │   ├── infrastructure_generation.py
│   │   │       │   │   ├── resource_operations.py
│   │   │       │   │   ├── security_scanning.py
│   │   │       │   │   └── session_management.py
│   │   │       │   └── utils
│   │   │       │       ├── __init__.py
│   │   │       │       └── validation.py
│   │   │       ├── infrastructure_generator.py
│   │   │       ├── models
│   │   │       │   ├── __init__.py
│   │   │       │   └── models.py
│   │   │       ├── schema_manager.py
│   │   │       ├── server.py
│   │   │       └── static
│   │   │           └── __init__.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── run_tests.sh
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── test_aws_client.py
│   │   │   ├── test_checkov_install.py
│   │   │   ├── test_cloud_control_utils.py
│   │   │   ├── test_context.py
│   │   │   ├── test_errors.py
│   │   │   ├── test_explanation.py
│   │   │   ├── test_iac_generator.py
│   │   │   ├── test_infrastructure_generation.py
│   │   │   ├── test_infrastructure_generator.py
│   │   │   ├── test_models.py
│   │   │   ├── test_resource_operations.py
│   │   │   ├── test_schema_manager.py
│   │   │   ├── test_security_scanning.py
│   │   │   ├── test_server.py
│   │   │   ├── test_session_management.py
│   │   │   └── test_validation.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── cdk-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── cdk_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── core
│   │   │       │   ├── __init__.py
│   │   │       │   ├── resources.py
│   │   │       │   ├── search_utils.py
│   │   │       │   ├── server.py
│   │   │       │   └── tools.py
│   │   │       ├── data
│   │   │       │   ├── __init__.py
│   │   │       │   ├── cdk_nag_parser.py
│   │   │       │   ├── construct_descriptions.py
│   │   │       │   ├── genai_cdk_loader.py
│   │   │       │   ├── lambda_layer_parser.py
│   │   │       │   ├── lambda_powertools_loader.py
│   │   │       │   ├── schema_generator.py
│   │   │       │   └── solutions_constructs_parser.py
│   │   │       ├── server.py
│   │   │       └── static
│   │   │           ├── __init__.py
│   │   │           ├── CDK_GENERAL_GUIDANCE.md
│   │   │           ├── CDK_NAG_GUIDANCE.md
│   │   │           └── lambda_powertools
│   │   │               ├── bedrock.md
│   │   │               ├── cdk.md
│   │   │               ├── dependencies.md
│   │   │               ├── index.md
│   │   │               ├── insights.md
│   │   │               ├── logging.md
│   │   │               ├── metrics.md
│   │   │               └── tracing.md
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── core
│   │   │   │   ├── test_resources_enhanced.py
│   │   │   │   ├── test_resources.py
│   │   │   │   ├── test_search_utils.py
│   │   │   │   ├── test_server.py
│   │   │   │   └── test_tools.py
│   │   │   └── data
│   │   │       ├── test_cdk_nag_parser.py
│   │   │       ├── test_genai_cdk_loader.py
│   │   │       ├── test_lambda_powertools_loader.py
│   │   │       ├── test_schema_generator.py
│   │   │       └── test_solutions_constructs_parser.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── cfn-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── cfn_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── aws_client.py
│   │   │       ├── cloud_control_utils.py
│   │   │       ├── context.py
│   │   │       ├── errors.py
│   │   │       ├── iac_generator.py
│   │   │       ├── schema_manager.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── run_tests.sh
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── test_aws_client.py
│   │   │   ├── test_cloud_control_utils.py
│   │   │   ├── test_errors.py
│   │   │   ├── test_iac_generator.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   ├── test_schema_manager.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── cloudtrail-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── cloudtrail_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── common.py
│   │   │       ├── models.py
│   │   │       ├── server.py
│   │   │       └── tools.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   ├── test_models.py
│   │   │   ├── test_server.py
│   │   │   └── test_tools.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── cloudwatch-appsignals-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── cloudwatch_appsignals_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── audit_presentation_utils.py
│   │   │       ├── audit_utils.py
│   │   │       ├── aws_clients.py
│   │   │       ├── canary_utils.py
│   │   │       ├── server.py
│   │   │       ├── service_audit_utils.py
│   │   │       ├── service_tools.py
│   │   │       ├── sli_report_client.py
│   │   │       ├── slo_tools.py
│   │   │       ├── trace_tools.py
│   │   │       └── utils.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── conftest.py
│   │   │   ├── test_audit_presentation_utils.py
│   │   │   ├── test_audit_utils.py
│   │   │   ├── test_aws_profile.py
│   │   │   ├── test_canary_utils.py
│   │   │   ├── test_initialization.py
│   │   │   ├── test_server_audit_functions.py
│   │   │   ├── test_server_audit_tools.py
│   │   │   ├── test_server.py
│   │   │   ├── test_service_audit_utils.py
│   │   │   ├── test_service_tools_operations.py
│   │   │   ├── test_sli_report_client.py
│   │   │   ├── test_slo_tools.py
│   │   │   └── test_utils.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── cloudwatch-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── cloudwatch_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── cloudwatch_alarms
│   │   │       │   ├── models.py
│   │   │       │   └── tools.py
│   │   │       ├── cloudwatch_logs
│   │   │       │   ├── models.py
│   │   │       │   └── tools.py
│   │   │       ├── cloudwatch_metrics
│   │   │       │   ├── cloudformation_template_generator.py
│   │   │       │   ├── constants.py
│   │   │       │   ├── data
│   │   │       │   │   └── metric_metadata.json
│   │   │       │   ├── metric_analyzer.py
│   │   │       │   ├── metric_data_decomposer.py
│   │   │       │   ├── models.py
│   │   │       │   └── tools.py
│   │   │       ├── common.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── cloudwatch_alarms
│   │   │   │   ├── test_active_alarms.py
│   │   │   │   ├── test_alarm_history_integration.py
│   │   │   │   ├── test_alarm_history.py
│   │   │   │   └── test_alarms_error_handling.py
│   │   │   ├── cloudwatch_logs
│   │   │   │   ├── test_logs_error_handling.py
│   │   │   │   ├── test_logs_models.py
│   │   │   │   └── test_logs_server.py
│   │   │   ├── cloudwatch_metrics
│   │   │   │   ├── test_analyze_metric.py
│   │   │   │   ├── test_cloudformation_template_generator.py
│   │   │   │   ├── test_decomposer_trend.py
│   │   │   │   ├── test_metric_analyzer.py
│   │   │   │   ├── test_metrics_error_handling.py
│   │   │   │   ├── test_metrics_models.py
│   │   │   │   ├── test_metrics_server.py
│   │   │   │   ├── test_seasonal_detector.py
│   │   │   │   ├── test_seasonality_enum.py
│   │   │   │   ├── test_utils.py
│   │   │   │   └── test_validation_error.py
│   │   │   ├── test_common_and_server.py
│   │   │   ├── test_init.py
│   │   │   └── test_main.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── code-doc-gen-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── code_doc_gen_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── server.py
│   │   │       └── utils
│   │   │           ├── doc_generator.py
│   │   │           ├── models.py
│   │   │           ├── repomix_manager.py
│   │   │           └── templates.py
│   │   ├── CHANGELOG.md
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── test_doc_generator_edge_cases.py
│   │   │   ├── test_doc_generator.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   ├── test_repomix_manager_scenarios.py
│   │   │   ├── test_repomix_manager.py
│   │   │   ├── test_repomix_statistics.py
│   │   │   ├── test_server_extended.py
│   │   │   ├── test_server.py
│   │   │   └── test_templates.py
│   │   └── uv.lock
│   ├── core-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── core_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── server.py
│   │   │       └── static
│   │   │           ├── __init__.py
│   │   │           └── PROMPT_UNDERSTANDING.md
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── README.md
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   ├── test_response_types.py
│   │   │   ├── test_server.py
│   │   │   └── test_static.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── cost-explorer-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── cost_explorer_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── comparison_handler.py
│   │   │       ├── constants.py
│   │   │       ├── cost_usage_handler.py
│   │   │       ├── forecasting_handler.py
│   │   │       ├── helpers.py
│   │   │       ├── metadata_handler.py
│   │   │       ├── models.py
│   │   │       ├── server.py
│   │   │       └── utility_handler.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── test_comparison_handler.py
│   │   │   ├── test_cost_usage_handler.py
│   │   │   ├── test_forecasting_handler.py
│   │   │   ├── test_helpers.py
│   │   │   ├── test_metadata_handler.py
│   │   │   ├── test_models.py
│   │   │   ├── test_server.py
│   │   │   └── test_utility_handler.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── documentdb-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   └── documentdb_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── analytic_tools.py
│   │   │       ├── config.py
│   │   │       ├── connection_tools.py
│   │   │       ├── db_management_tools.py
│   │   │       ├── query_tools.py
│   │   │       ├── server.py
│   │   │       └── write_tools.py
│   │   ├── CHANGELOG.md
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── conftest.py
│   │   │   ├── test_analytic_tools.py
│   │   │   ├── test_connection_tools.py
│   │   │   ├── test_db_management_tools.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   ├── test_query_tools.py
│   │   │   └── test_write_tools.py
│   │   └── uv.lock
│   ├── dynamodb-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── dynamodb_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── common.py
│   │   │       ├── database_analysis_queries.py
│   │   │       ├── database_analyzers.py
│   │   │       ├── markdown_formatter.py
│   │   │       ├── prompts
│   │   │       │   └── dynamodb_architect.md
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── evals
│   │   │   │   ├── dynamic_evaluators.py
│   │   │   │   ├── evaluation_registry.py
│   │   │   │   ├── logging_config.py
│   │   │   │   ├── multiturn_evaluator.py
│   │   │   │   ├── README.md
│   │   │   │   ├── scenarios.py
│   │   │   │   └── test_dspy_evals.py
│   │   │   ├── test_dynamodb_server.py
│   │   │   ├── test_markdown_formatter.py
│   │   │   └── test_source_db_integration.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── ecs-mcp-server
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── ecs_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── api
│   │   │       │   ├── __init__.py
│   │   │       │   ├── containerize.py
│   │   │       │   ├── delete.py
│   │   │       │   ├── ecs_troubleshooting.py
│   │   │       │   ├── infrastructure.py
│   │   │       │   ├── resource_management.py
│   │   │       │   ├── status.py
│   │   │       │   └── troubleshooting_tools
│   │   │       │       ├── __init__.py
│   │   │       │       ├── detect_image_pull_failures.py
│   │   │       │       ├── fetch_cloudformation_status.py
│   │   │       │       ├── fetch_network_configuration.py
│   │   │       │       ├── fetch_service_events.py
│   │   │       │       ├── fetch_task_failures.py
│   │   │       │       ├── fetch_task_logs.py
│   │   │       │       ├── get_ecs_troubleshooting_guidance.py
│   │   │       │       └── utils.py
│   │   │       ├── main.py
│   │   │       ├── modules
│   │   │       │   ├── __init__.py
│   │   │       │   ├── aws_knowledge_proxy.py
│   │   │       │   ├── containerize.py
│   │   │       │   ├── delete.py
│   │   │       │   ├── deployment_status.py
│   │   │       │   ├── infrastructure.py
│   │   │       │   ├── resource_management.py
│   │   │       │   └── troubleshooting.py
│   │   │       ├── templates
│   │   │       │   ├── ecr_infrastructure.json
│   │   │       │   └── ecs_infrastructure.json
│   │   │       └── utils
│   │   │           ├── arn_parser.py
│   │   │           ├── aws.py
│   │   │           ├── config.py
│   │   │           ├── docker.py
│   │   │           ├── security.py
│   │   │           ├── templates.py
│   │   │           └── time_utils.py
│   │   ├── DEVELOPMENT.md
│   │   ├── pyproject.toml
│   │   ├── pyrightconfig.json
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── integ
│   │   │   │   └── mcp-inspector
│   │   │   │       ├── .gitignore
│   │   │   │       ├── README.md
│   │   │   │       ├── run-tests.sh
│   │   │   │       └── scenarios
│   │   │   │           ├── 01_comprehensive_troubleshooting
│   │   │   │           │   ├── 01_create.sh
│   │   │   │           │   ├── 02_validate.sh
│   │   │   │           │   ├── 03_cleanup.sh
│   │   │   │           │   ├── description.txt
│   │   │   │           │   └── utils
│   │   │   │           │       ├── mcp_helpers.sh
│   │   │   │           │       └── validation_helpers.sh
│   │   │   │           └── 02_test_knowledge_proxy_tools
│   │   │   │               ├── 01_create.sh
│   │   │   │               ├── 02_validate.sh
│   │   │   │               ├── 03_cleanup.sh
│   │   │   │               ├── description.txt
│   │   │   │               └── utils
│   │   │   │                   ├── knowledge_validation_helpers.sh
│   │   │   │                   └── mcp_knowledge_helpers.sh
│   │   │   ├── llm_testing
│   │   │   │   ├── invalid_cfn_template.yaml
│   │   │   │   ├── README.md
│   │   │   │   ├── run_tests.sh
│   │   │   │   ├── scenarios
│   │   │   │   │   ├── 01_cloudformation_failure
│   │   │   │   │   │   ├── 01_create.sh
│   │   │   │   │   │   ├── 02_validate.sh
│   │   │   │   │   │   ├── 03_prompts.txt
│   │   │   │   │   │   ├── 04_evaluation.md
│   │   │   │   │   │   ├── 05_cleanup.sh
│   │   │   │   │   │   └── description.txt
│   │   │   │   │   ├── 02_service_failure
│   │   │   │   │   │   ├── 01_create.sh
│   │   │   │   │   │   ├── 02_validate.sh
│   │   │   │   │   │   ├── 03_prompts.txt
│   │   │   │   │   │   ├── 04_evaluation.md
│   │   │   │   │   │   ├── 05_cleanup.sh
│   │   │   │   │   │   └── description.txt
│   │   │   │   │   ├── 03_task_exit_failure
│   │   │   │   │   │   ├── 01_create.sh
│   │   │   │   │   │   ├── 02_validate.sh
│   │   │   │   │   │   ├── 03_prompts.txt
│   │   │   │   │   │   ├── 04_evaluation.md
│   │   │   │   │   │   ├── 05_cleanup.sh
│   │   │   │   │   │   └── description.txt
│   │   │   │   │   ├── 04_network_configuration_failure
│   │   │   │   │   │   ├── 01_create.sh
│   │   │   │   │   │   ├── 02_validate.sh
│   │   │   │   │   │   ├── 03_prompts.txt
│   │   │   │   │   │   ├── 05_cleanup.sh
│   │   │   │   │   │   └── description.txt
│   │   │   │   │   ├── 05_resource_constraint_failure
│   │   │   │   │   │   ├── 01_create.sh
│   │   │   │   │   │   ├── 02_validate.sh
│   │   │   │   │   │   ├── 03_prompts.txt
│   │   │   │   │   │   ├── 05_cleanup.sh
│   │   │   │   │   │   └── description.txt
│   │   │   │   │   └── 06_load_balancer_failure
│   │   │   │   │       ├── 01_create.sh
│   │   │   │   │       ├── 02_validate.sh
│   │   │   │   │       ├── 03_prompts.txt
│   │   │   │   │       ├── 05_cleanup.sh
│   │   │   │   │       └── description.txt
│   │   │   │   ├── SCRIPT_IMPROVEMENTS.md
│   │   │   │   └── utils
│   │   │   │       ├── aws_helpers.sh
│   │   │   │       └── evaluation_template.md
│   │   │   └── unit
│   │   │       ├── __init__.py
│   │   │       ├── api
│   │   │       │   ├── conftest.py
│   │   │       │   ├── test_delete_api.py
│   │   │       │   ├── test_ecs_troubleshooting.py
│   │   │       │   ├── test_resource_management_api.py
│   │   │       │   └── troubleshooting_tools
│   │   │       │       └── test_fetch_network_configuration.py
│   │   │       ├── conftest.py
│   │   │       ├── modules
│   │   │       │   ├── test_aws_knowledge_proxy.py
│   │   │       │   └── test_resource_management_module.py
│   │   │       ├── test_aws_role_utils.py
│   │   │       ├── test_aws_utils.py
│   │   │       ├── test_containerize.py
│   │   │       ├── test_delete.py
│   │   │       ├── test_docker_utils.py
│   │   │       ├── test_docker_with_role.py
│   │   │       ├── test_image_pull_failure_extended.py
│   │   │       ├── test_image_pull_failure.py
│   │   │       ├── test_infrastructure_role.py
│   │   │       ├── test_infrastructure.py
│   │   │       ├── test_integration.py
│   │   │       ├── test_main.py
│   │   │       ├── test_resource_management_api_operation.py
│   │   │       ├── test_resource_management_tool.py
│   │   │       ├── test_resource_management.py
│   │   │       ├── test_security_integration.py
│   │   │       ├── test_status_pytest.py
│   │   │       ├── test_status.py
│   │   │       ├── troubleshooting_tools
│   │   │       │   ├── __init__.py
│   │   │       │   ├── conftest.py
│   │   │       │   ├── test_detect_image_pull_failures.py
│   │   │       │   ├── test_fetch_cloudformation_status.py
│   │   │       │   ├── test_fetch_service_events.py
│   │   │       │   ├── test_fetch_task_failures.py
│   │   │       │   ├── test_fetch_task_logs.py
│   │   │       │   ├── test_get_ecs_troubleshooting_guidance.py
│   │   │       │   ├── test_is_ecr_image_security.py
│   │   │       │   └── test_utils.py
│   │   │       └── utils
│   │   │           ├── __init__.py
│   │   │           ├── async_test_utils.py
│   │   │           ├── test_arn_parser.py
│   │   │           ├── test_config.py
│   │   │           ├── test_docker.py
│   │   │           ├── test_response_sanitization.py
│   │   │           ├── test_security_extended.py
│   │   │           ├── test_security.py
│   │   │           ├── test_templates.py
│   │   │           └── test_time_utils.py
│   │   └── uv.lock
│   ├── eks-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── eks_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── aws_helper.py
│   │   │       ├── cloudwatch_handler.py
│   │   │       ├── cloudwatch_metrics_guidance_handler.py
│   │   │       ├── consts.py
│   │   │       ├── data
│   │   │       │   └── eks_cloudwatch_metrics_guidance.json
│   │   │       ├── eks_kb_handler.py
│   │   │       ├── eks_stack_handler.py
│   │   │       ├── iam_handler.py
│   │   │       ├── insights_handler.py
│   │   │       ├── k8s_apis.py
│   │   │       ├── k8s_client_cache.py
│   │   │       ├── k8s_handler.py
│   │   │       ├── logging_helper.py
│   │   │       ├── models.py
│   │   │       ├── scripts
│   │   │       │   └── update_eks_cloudwatch_metrics_guidance.py
│   │   │       ├── server.py
│   │   │       ├── templates
│   │   │       │   ├── eks-templates
│   │   │       │   │   └── eks-with-vpc.yaml
│   │   │       │   └── k8s-templates
│   │   │       │       ├── deployment.yaml
│   │   │       │       └── service.yaml
│   │   │       └── vpc_config_handler.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── test_aws_helper.py
│   │   │   ├── test_cloudwatch_handler.py
│   │   │   ├── test_cloudwatch_metrics_guidance_handler.py
│   │   │   ├── test_eks_kb_handler.py
│   │   │   ├── test_eks_stack_handler.py
│   │   │   ├── test_iam_handler.py
│   │   │   ├── test_init.py
│   │   │   ├── test_insights_handler.py
│   │   │   ├── test_k8s_apis.py
│   │   │   ├── test_k8s_client_cache.py
│   │   │   ├── test_k8s_handler.py
│   │   │   ├── test_logging_helper.py
│   │   │   ├── test_main.py
│   │   │   ├── test_models.py
│   │   │   ├── test_server.py
│   │   │   └── test_vpc_config_handler.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── elasticache-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── elasticache_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── common
│   │   │       │   ├── __init__.py
│   │   │       │   ├── connection.py
│   │   │       │   ├── decorators.py
│   │   │       │   └── server.py
│   │   │       ├── context.py
│   │   │       ├── main.py
│   │   │       └── tools
│   │   │           ├── __init__.py
│   │   │           ├── cc
│   │   │           │   ├── __init__.py
│   │   │           │   ├── connect.py
│   │   │           │   ├── create.py
│   │   │           │   ├── delete.py
│   │   │           │   ├── describe.py
│   │   │           │   ├── modify.py
│   │   │           │   ├── parsers.py
│   │   │           │   └── processors.py
│   │   │           ├── ce
│   │   │           │   ├── __init__.py
│   │   │           │   └── get_cost_and_usage.py
│   │   │           ├── cw
│   │   │           │   ├── __init__.py
│   │   │           │   └── get_metric_statistics.py
│   │   │           ├── cwlogs
│   │   │           │   ├── __init__.py
│   │   │           │   ├── create_log_group.py
│   │   │           │   ├── describe_log_groups.py
│   │   │           │   ├── describe_log_streams.py
│   │   │           │   ├── filter_log_events.py
│   │   │           │   └── get_log_events.py
│   │   │           ├── firehose
│   │   │           │   ├── __init__.py
│   │   │           │   └── list_delivery_streams.py
│   │   │           ├── misc
│   │   │           │   ├── __init__.py
│   │   │           │   ├── batch_apply_update_action.py
│   │   │           │   ├── batch_stop_update_action.py
│   │   │           │   ├── describe_cache_engine_versions.py
│   │   │           │   ├── describe_engine_default_parameters.py
│   │   │           │   ├── describe_events.py
│   │   │           │   └── describe_service_updates.py
│   │   │           ├── rg
│   │   │           │   ├── __init__.py
│   │   │           │   ├── complete_migration.py
│   │   │           │   ├── connect.py
│   │   │           │   ├── create.py
│   │   │           │   ├── delete.py
│   │   │           │   ├── describe.py
│   │   │           │   ├── modify.py
│   │   │           │   ├── parsers.py
│   │   │           │   ├── processors.py
│   │   │           │   ├── start_migration.py
│   │   │           │   └── test_migration.py
│   │   │           └── serverless
│   │   │               ├── __init__.py
│   │   │               ├── connect.py
│   │   │               ├── create.py
│   │   │               ├── delete.py
│   │   │               ├── describe.py
│   │   │               ├── models.py
│   │   │               └── modify.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── test_connection.py
│   │   │   ├── test_decorators.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   └── tools
│   │   │       ├── cc
│   │   │       │   ├── __init__.py
│   │   │       │   ├── test_connect_additional.py
│   │   │       │   ├── test_connect_coverage_additional.py
│   │   │       │   ├── test_connect_coverage.py
│   │   │       │   ├── test_connect.py
│   │   │       │   ├── test_create_additional.py
│   │   │       │   ├── test_create.py
│   │   │       │   ├── test_delete.py
│   │   │       │   ├── test_describe.py
│   │   │       │   ├── test_modify.py
│   │   │       │   ├── test_parsers.py
│   │   │       │   └── test_processors.py
│   │   │       ├── ce
│   │   │       │   ├── __init__.py
│   │   │       │   └── test_get_cost_and_usage.py
│   │   │       ├── cw
│   │   │       │   └── test_get_metric_statistics.py
│   │   │       ├── cwlogs
│   │   │       │   ├── __init__.py
│   │   │       │   ├── test_create_log_group.py
│   │   │       │   ├── test_describe_log_groups.py
│   │   │       │   ├── test_describe_log_streams.py
│   │   │       │   ├── test_filter_log_events.py
│   │   │       │   └── test_get_log_events.py
│   │   │       ├── firehose
│   │   │       │   └── test_list_delivery_streams.py
│   │   │       ├── misc
│   │   │       │   ├── __init__.py
│   │   │       │   ├── test_batch_apply_update_action.py
│   │   │       │   ├── test_batch_stop_update_action.py
│   │   │       │   ├── test_describe_cache_engine_versions.py
│   │   │       │   ├── test_describe_engine_default_parameters.py
│   │   │       │   ├── test_describe_events.py
│   │   │       │   └── test_describe_service_updates.py
│   │   │       ├── rg
│   │   │       │   ├── __init__.py
│   │   │       │   ├── test_complete_migration.py
│   │   │       │   ├── test_connect_additional.py
│   │   │       │   ├── test_connect_coverage_additional.py
│   │   │       │   ├── test_connect_optional_fields.py
│   │   │       │   ├── test_connect_partial_coverage.py
│   │   │       │   ├── test_connect.py
│   │   │       │   ├── test_create.py
│   │   │       │   ├── test_delete.py
│   │   │       │   ├── test_describe.py
│   │   │       │   ├── test_modify.py
│   │   │       │   ├── test_parsers.py
│   │   │       │   ├── test_processors.py
│   │   │       │   ├── test_start_migration.py
│   │   │       │   └── test_test_migration.py
│   │   │       └── serverless
│   │   │           ├── test_connect_additional.py
│   │   │           ├── test_connect_coverage_additional.py
│   │   │           ├── test_connect_optional_fields.py
│   │   │           ├── test_connect.py
│   │   │           ├── test_create.py
│   │   │           ├── test_delete.py
│   │   │           ├── test_describe.py
│   │   │           └── test_modify.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── finch-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── finch_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── consts.py
│   │   │       ├── models.py
│   │   │       ├── server.py
│   │   │       └── utils
│   │   │           ├── __init__.py
│   │   │           ├── build.py
│   │   │           ├── common.py
│   │   │           ├── ecr.py
│   │   │           ├── push.py
│   │   │           └── vm.py
│   │   ├── CHANGELOG.md
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── test_cli_flags.py
│   │   │   ├── test_logging_configuration.py
│   │   │   ├── test_server.py
│   │   │   ├── test_utils_build.py
│   │   │   ├── test_utils_common.py
│   │   │   ├── test_utils_ecr.py
│   │   │   ├── test_utils_push.py
│   │   │   └── test_utils_vm.py
│   │   └── uv.lock
│   ├── frontend-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── frontend_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── server.py
│   │   │       ├── static
│   │   │       │   └── react
│   │   │       │       ├── essential-knowledge.md
│   │   │       │       └── troubleshooting.md
│   │   │       └── utils
│   │   │           ├── __init__.py
│   │   │           └── file_utils.py
│   │   ├── CHANGELOG.md
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── test_file_utils.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   └── test_server.py
│   │   └── uv.lock
│   ├── git-repo-research-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── git_repo_research_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── defaults.py
│   │   │       ├── embeddings.py
│   │   │       ├── github_search.py
│   │   │       ├── indexer.py
│   │   │       ├── models.py
│   │   │       ├── repository.py
│   │   │       ├── search.py
│   │   │       ├── server.py
│   │   │       └── utils.py
│   │   ├── CHANGELOG.md
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── run_tests.sh
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── test_errors_repository.py
│   │   │   ├── test_github_search_edge_cases.py
│   │   │   ├── test_graphql_github_search.py
│   │   │   ├── test_local_repository.py
│   │   │   ├── test_repository_utils.py
│   │   │   ├── test_rest_github_search.py
│   │   │   ├── test_search.py
│   │   │   ├── test_server.py
│   │   │   └── test_url_repository.py
│   │   └── uv.lock
│   ├── healthlake-mcp-server
│   │   ├── .dockerignore
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── healthlake_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── fhir_operations.py
│   │   │       ├── main.py
│   │   │       ├── models.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── CONTRIBUTING.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── examples
│   │   │   ├── mcp_config.json
│   │   │   └── README.md
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── conftest.py
│   │   │   ├── test_fhir_client_comprehensive.py
│   │   │   ├── test_fhir_error_scenarios.py
│   │   │   ├── test_fhir_operations.py
│   │   │   ├── test_integration_mock_based.py
│   │   │   ├── test_main_edge_cases.py
│   │   │   ├── test_main.py
│   │   │   ├── test_mcp_integration_coverage.py
│   │   │   ├── test_models_edge_cases.py
│   │   │   ├── test_models.py
│   │   │   ├── test_readonly_mode.py
│   │   │   ├── test_server_core.py
│   │   │   ├── test_server_error_handling.py
│   │   │   ├── test_server_mcp_handlers.py
│   │   │   ├── test_server_toolhandler.py
│   │   │   └── test_server_validation.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── iam-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── iam_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── aws_client.py
│   │   │       ├── context.py
│   │   │       ├── errors.py
│   │   │       ├── models.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── DESIGN_COMPLIANCE.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── examples
│   │   │   ├── get_policy_document_example.py
│   │   │   └── inline_policy_demo.py
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── run_tests.sh
│   │   ├── tests
│   │   │   ├── test_context.py
│   │   │   ├── test_errors.py
│   │   │   ├── test_inline_policies.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── lambda-tool-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── lambda_tool_mcp_server
│   │   │       ├── __init__.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── examples
│   │   │   ├── README.md
│   │   │   └── sample_functions
│   │   │       ├── customer-create
│   │   │       │   └── app.py
│   │   │       ├── customer-id-from-email
│   │   │       │   └── app.py
│   │   │       ├── customer-info-from-id
│   │   │       │   └── app.py
│   │   │       └── template.yml
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── .gitignore
│   │   │   ├── conftest.py
│   │   │   ├── README.md
│   │   │   ├── test_format_lambda_response.py
│   │   │   ├── test_integration_coverage.py
│   │   │   ├── test_integration.py
│   │   │   ├── test_register_lambda_functions.py
│   │   │   ├── test_schema_integration.py
│   │   │   ├── test_server_coverage_additional.py
│   │   │   ├── test_server_coverage.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── mcp-lambda-handler
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   └── mcp_lambda_handler
│   │   │       ├── __init__.py
│   │   │       ├── mcp_lambda_handler.py
│   │   │       ├── session.py
│   │   │       └── types.py
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   └── test_lambda_handler.py
│   │   └── uv.lock
│   ├── memcached-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── memcached_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── common
│   │   │       │   ├── config.py
│   │   │       │   ├── connection.py
│   │   │       │   └── server.py
│   │   │       ├── context.py
│   │   │       ├── main.py
│   │   │       └── tools
│   │   │           └── cache.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── ELASTICACHECONNECT.md
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── test_cache_readonly.py
│   │   │   ├── test_cache.py
│   │   │   ├── test_connection.py
│   │   │   ├── test_init.py
│   │   │   └── test_main.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── mysql-mcp-server
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── mysql_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── connection
│   │   │       │   ├── __init__.py
│   │   │       │   ├── abstract_db_connection.py
│   │   │       │   ├── asyncmy_pool_connection.py
│   │   │       │   ├── db_connection_singleton.py
│   │   │       │   └── rds_data_api_connection.py
│   │   │       ├── mutable_sql_detector.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── conftest.py
│   │   │   ├── test_abstract_db_connection.py
│   │   │   ├── test_asyncmy_pool_connection.py
│   │   │   ├── test_db_connection_singleton.py
│   │   │   ├── test_rds_data_api_connection.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── nova-canvas-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── nova_canvas_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── consts.py
│   │   │       ├── models.py
│   │   │       ├── novacanvas.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── .gitignore
│   │   │   ├── conftest.py
│   │   │   ├── README.md
│   │   │   ├── test_models.py
│   │   │   ├── test_novacanvas.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── openapi-mcp-server
│   │   ├── .coveragerc
│   │   ├── .dockerignore
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── AUTHENTICATION.md
│   │   ├── AWS_BEST_PRACTICES.md
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── openapi_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── api
│   │   │       │   ├── __init__.py
│   │   │       │   └── config.py
│   │   │       ├── auth
│   │   │       │   ├── __init__.py
│   │   │       │   ├── api_key_auth.py
│   │   │       │   ├── auth_cache.py
│   │   │       │   ├── auth_errors.py
│   │   │       │   ├── auth_factory.py
│   │   │       │   ├── auth_protocol.py
│   │   │       │   ├── auth_provider.py
│   │   │       │   ├── base_auth.py
│   │   │       │   ├── basic_auth.py
│   │   │       │   ├── bearer_auth.py
│   │   │       │   ├── cognito_auth.py
│   │   │       │   └── register.py
│   │   │       ├── patch
│   │   │       │   └── __init__.py
│   │   │       ├── prompts
│   │   │       │   ├── __init__.py
│   │   │       │   ├── generators
│   │   │       │   │   ├── __init__.py
│   │   │       │   │   ├── operation_prompts.py
│   │   │       │   │   └── workflow_prompts.py
│   │   │       │   ├── models.py
│   │   │       │   └── prompt_manager.py
│   │   │       ├── server.py
│   │   │       └── utils
│   │   │           ├── __init__.py
│   │   │           ├── cache_provider.py
│   │   │           ├── config.py
│   │   │           ├── error_handler.py
│   │   │           ├── http_client.py
│   │   │           ├── metrics_provider.py
│   │   │           ├── openapi_validator.py
│   │   │           └── openapi.py
│   │   ├── CHANGELOG.md
│   │   ├── DEPLOYMENT.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── OBSERVABILITY.md
│   │   ├── pyproject.toml
│   │   ├── pyrightconfig.json
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── api
│   │   │   │   └── test_config.py
│   │   │   ├── auth
│   │   │   │   ├── test_api_key_auth.py
│   │   │   │   ├── test_auth_cache.py
│   │   │   │   ├── test_auth_errors.py
│   │   │   │   ├── test_auth_factory_caching.py
│   │   │   │   ├── test_auth_factory_coverage.py
│   │   │   │   ├── test_auth_factory.py
│   │   │   │   ├── test_auth_protocol_additional.py
│   │   │   │   ├── test_auth_protocol_boost.py
│   │   │   │   ├── test_auth_protocol_coverage.py
│   │   │   │   ├── test_auth_protocol_extended.py
│   │   │   │   ├── test_auth_protocol_improved.py
│   │   │   │   ├── test_auth_protocol.py
│   │   │   │   ├── test_auth_provider_additional.py
│   │   │   │   ├── test_base_auth_coverage.py
│   │   │   │   ├── test_base_auth.py
│   │   │   │   ├── test_basic_auth.py
│   │   │   │   ├── test_bearer_auth.py
│   │   │   │   ├── test_cognito_auth_additional_coverage.py
│   │   │   │   ├── test_cognito_auth_boost_coverage.py
│   │   │   │   ├── test_cognito_auth_client_credentials.py
│   │   │   │   ├── test_cognito_auth_coverage_boost.py
│   │   │   │   ├── test_cognito_auth_exceptions.py
│   │   │   │   ├── test_cognito_auth.py
│   │   │   │   ├── test_register_coverage.py
│   │   │   │   └── test_register.py
│   │   │   ├── prompts
│   │   │   │   ├── standalone
│   │   │   │   │   ├── test_operation_prompt.py
│   │   │   │   │   ├── test_prompt_arguments.py
│   │   │   │   │   └── test_secure_operation_prompt.py
│   │   │   │   ├── test_mcp_prompt_manager_integration.py
│   │   │   │   ├── test_mcp_prompt_manager.py
│   │   │   │   ├── test_models_dict_method.py
│   │   │   │   ├── test_operation_prompts_extended.py
│   │   │   │   ├── test_prompt_manager_additional.py
│   │   │   │   ├── test_prompt_manager_comprehensive.py
│   │   │   │   ├── test_prompt_manager_coverage.py
│   │   │   │   └── test_prompt_registration.py
│   │   │   ├── README.md
│   │   │   ├── test_api_name.py
│   │   │   ├── test_cache_coverage_89.py
│   │   │   ├── test_client.py
│   │   │   ├── test_coverage_boost.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main_extended.py
│   │   │   ├── test_main.py
│   │   │   ├── test_openapi_coverage_89.py
│   │   │   ├── test_server_auth_errors.py
│   │   │   ├── test_server_coverage_boost_2.py
│   │   │   ├── test_server_coverage_boost.py
│   │   │   ├── test_server_exception_handling.py
│   │   │   ├── test_server_extended.py
│   │   │   ├── test_server_httpx_version.py
│   │   │   ├── test_server_part1.py
│   │   │   ├── test_server_route_logging.py
│   │   │   ├── test_server_signal_handlers.py
│   │   │   ├── test_server.py
│   │   │   └── utils
│   │   │       ├── test_cache_provider.py
│   │   │       ├── test_error_handler_boost.py
│   │   │       ├── test_error_handler_extended.py
│   │   │       ├── test_error_handler_fix.py
│   │   │       ├── test_error_handler.py
│   │   │       ├── test_http_client_comprehensive.py
│   │   │       ├── test_http_client_extended.py
│   │   │       ├── test_http_client_extended2.py
│   │   │       ├── test_http_client_import_error.py
│   │   │       ├── test_http_client.py
│   │   │       ├── test_metrics_provider_decorators.py
│   │   │       ├── test_metrics_provider_extended2.py
│   │   │       ├── test_metrics_provider_prometheus.py
│   │   │       ├── test_metrics_provider.py
│   │   │       ├── test_openapi_validator.py
│   │   │       └── test_openapi.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── postgres-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── postgres_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── connection
│   │   │       │   ├── __init__.py
│   │   │       │   ├── abstract_db_connection.py
│   │   │       │   ├── db_connection_singleton.py
│   │   │       │   ├── psycopg_pool_connection.py
│   │   │       │   └── rds_api_connection.py
│   │   │       ├── mutable_sql_detector.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── conftest.py
│   │   │   ├── test_psycopg_connector.py
│   │   │   ├── test_server.py
│   │   │   └── test_singleton.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── prometheus-mcp-server
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── prometheus_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── consts.py
│   │   │       ├── models.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── conftest.py
│   │   │   ├── test_aws_credentials.py
│   │   │   ├── test_config_manager.py
│   │   │   ├── test_consts.py
│   │   │   ├── test_coverage_gaps.py
│   │   │   ├── test_coverage_improvement.py
│   │   │   ├── test_final_coverage.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   ├── test_models.py
│   │   │   ├── test_prometheus_client.py
│   │   │   ├── test_prometheus_connection.py
│   │   │   ├── test_security_validator.py
│   │   │   ├── test_server_coverage.py
│   │   │   ├── test_tools.py
│   │   │   └── test_workspace_config.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── redshift-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── redshift_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── consts.py
│   │   │       ├── models.py
│   │   │       ├── redshift.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   ├── test_redshift.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── s3-tables-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── s3_tables_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── constants.py
│   │   │       ├── database.py
│   │   │       ├── engines
│   │   │       │   ├── __init__.py
│   │   │       │   └── pyiceberg.py
│   │   │       ├── file_processor
│   │   │       │   ├── __init__.py
│   │   │       │   ├── csv.py
│   │   │       │   ├── parquet.py
│   │   │       │   └── utils.py
│   │   │       ├── models.py
│   │   │       ├── namespaces.py
│   │   │       ├── resources.py
│   │   │       ├── s3_operations.py
│   │   │       ├── server.py
│   │   │       ├── table_buckets.py
│   │   │       ├── tables.py
│   │   │       └── utils.py
│   │   ├── CHANGELOG.md
│   │   ├── CONTEXT.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── test_csv.py
│   │   │   ├── test_database.py
│   │   │   ├── test_file_processor_utils.py
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   ├── test_namespaces.py
│   │   │   ├── test_parquet.py
│   │   │   ├── test_pyiceberg.py
│   │   │   ├── test_resources.py
│   │   │   ├── test_s3_operations.py
│   │   │   ├── test_server.py
│   │   │   ├── test_table_buckets.py
│   │   │   ├── test_tables.py
│   │   │   └── test_utils.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── stepfunctions-tool-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── stepfunctions_tool_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── aws_helper.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── .gitignore
│   │   │   ├── README.md
│   │   │   ├── test_aws_helper.py
│   │   │   ├── test_create_state_machine_tool.py
│   │   │   ├── test_filter_state_machines_by_tag.py
│   │   │   ├── test_format_state_machine_response.py
│   │   │   ├── test_get_schema_arn_from_state_machine_arn.py
│   │   │   ├── test_get_schema_from_registry.py
│   │   │   ├── test_invoke_express_state_machine_impl.py
│   │   │   ├── test_invoke_standard_state_machine_impl.py
│   │   │   ├── test_main.py
│   │   │   ├── test_register_state_machines.py
│   │   │   ├── test_sanitize_tool_name.py
│   │   │   ├── test_server.py
│   │   │   └── test_validate_state_machine_name.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── syntheticdata-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── syntheticdata_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── pandas_interpreter.py
│   │   │       ├── server.py
│   │   │       └── storage
│   │   │           ├── __init__.py
│   │   │           ├── base.py
│   │   │           ├── loader.py
│   │   │           └── s3.py
│   │   ├── CHANGELOG.md
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── conftest.py
│   │   │   ├── test_constants.py
│   │   │   ├── test_pandas_interpreter.py
│   │   │   ├── test_server.py
│   │   │   └── test_storage
│   │   │       ├── __init__.py
│   │   │       ├── test_loader.py
│   │   │       └── test_s3.py
│   │   └── uv.lock
│   ├── terraform-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── terraform_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── impl
│   │   │       │   ├── resources
│   │   │       │   │   ├── __init__.py
│   │   │       │   │   ├── terraform_aws_provider_resources_listing.py
│   │   │       │   │   └── terraform_awscc_provider_resources_listing.py
│   │   │       │   └── tools
│   │   │       │       ├── __init__.py
│   │   │       │       ├── execute_terraform_command.py
│   │   │       │       ├── execute_terragrunt_command.py
│   │   │       │       ├── run_checkov_scan.py
│   │   │       │       ├── search_aws_provider_docs.py
│   │   │       │       ├── search_awscc_provider_docs.py
│   │   │       │       ├── search_specific_aws_ia_modules.py
│   │   │       │       ├── search_user_provided_module.py
│   │   │       │       └── utils.py
│   │   │       ├── models
│   │   │       │   ├── __init__.py
│   │   │       │   └── models.py
│   │   │       ├── scripts
│   │   │       │   ├── generate_aws_provider_resources.py
│   │   │       │   ├── generate_awscc_provider_resources.py
│   │   │       │   └── scrape_aws_terraform_best_practices.py
│   │   │       ├── server.py
│   │   │       └── static
│   │   │           ├── __init__.py
│   │   │           ├── AWS_PROVIDER_RESOURCES.md
│   │   │           ├── AWS_TERRAFORM_BEST_PRACTICES.md
│   │   │           ├── AWSCC_PROVIDER_RESOURCES.md
│   │   │           ├── MCP_INSTRUCTIONS.md
│   │   │           └── TERRAFORM_WORKFLOW_GUIDE.md
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── __init__.py
│   │   │   ├── .gitignore
│   │   │   ├── conftest.py
│   │   │   ├── README.md
│   │   │   ├── test_command_impl.py
│   │   │   ├── test_execute_terraform_command.py
│   │   │   ├── test_execute_terragrunt_command.py
│   │   │   ├── test_models.py
│   │   │   ├── test_parameter_annotations.py
│   │   │   ├── test_resources.py
│   │   │   ├── test_run_checkov_scan.py
│   │   │   ├── test_search_user_provided_module.py
│   │   │   ├── test_server.py
│   │   │   ├── test_tool_implementations.py
│   │   │   ├── test_utils_additional.py
│   │   │   └── test_utils.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── timestream-for-influxdb-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── timestream_for_influxdb_mcp_server
│   │   │       ├── __init__.py
│   │   │       └── server.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── test_init.py
│   │   │   ├── test_main.py
│   │   │   └── test_server.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   ├── valkey-mcp-server
│   │   ├── .gitignore
│   │   ├── .python-version
│   │   ├── awslabs
│   │   │   ├── __init__.py
│   │   │   └── valkey_mcp_server
│   │   │       ├── __init__.py
│   │   │       ├── common
│   │   │       │   ├── __init__.py
│   │   │       │   ├── config.py
│   │   │       │   ├── connection.py
│   │   │       │   └── server.py
│   │   │       ├── context.py
│   │   │       ├── main.py
│   │   │       ├── tools
│   │   │       │   ├── __init__.py
│   │   │       │   ├── bitmap.py
│   │   │       │   ├── hash.py
│   │   │       │   ├── hyperloglog.py
│   │   │       │   ├── json.py
│   │   │       │   ├── list.py
│   │   │       │   ├── misc.py
│   │   │       │   ├── server_management.py
│   │   │       │   ├── set.py
│   │   │       │   ├── sorted_set.py
│   │   │       │   ├── stream.py
│   │   │       │   └── string.py
│   │   │       └── version.py
│   │   ├── CHANGELOG.md
│   │   ├── docker-healthcheck.sh
│   │   ├── Dockerfile
│   │   ├── ELASTICACHECONNECT.md
│   │   ├── LICENSE
│   │   ├── NOTICE
│   │   ├── pyproject.toml
│   │   ├── README.md
│   │   ├── tests
│   │   │   ├── test_bitmap.py
│   │   │   ├── test_config.py
│   │   │   ├── test_connection.py
│   │   │   ├── test_hash.py
│   │   │   ├── test_hyperloglog.py
│   │   │   ├── test_init.py
│   │   │   ├── test_json_additional.py
│   │   │   ├── test_json_readonly.py
│   │   │   ├── test_json.py
│   │   │   ├── test_list_additional.py
│   │   │   ├── test_list_readonly.py
│   │   │   ├── test_list.py
│   │   │   ├── test_main.py
│   │   │   ├── test_misc.py
│   │   │   ├── test_server_management.py
│   │   │   ├── test_set_readonly.py
│   │   │   ├── test_set.py
│   │   │   ├── test_sorted_set_additional.py
│   │   │   ├── test_sorted_set_readonly.py
│   │   │   ├── test_sorted_set.py
│   │   │   ├── test_stream_additional.py
│   │   │   ├── test_stream_readonly.py
│   │   │   ├── test_stream.py
│   │   │   └── test_string.py
│   │   ├── uv-requirements.txt
│   │   └── uv.lock
│   └── well-architected-security-mcp-server
│       ├── .python-version
│       ├── awslabs
│       │   └── well_architected_security_mcp_server
│       │       ├── __init__.py
│       │       ├── consts.py
│       │       ├── server.py
│       │       └── util
│       │           ├── __init__.py
│       │           ├── network_security.py
│       │           ├── prompt_utils.py
│       │           ├── resource_utils.py
│       │           ├── security_services.py
│       │           └── storage_security.py
│       ├── PROMPT_TEMPLATE.md
│       ├── pyproject.toml
│       ├── README.md
│       ├── tests
│       │   ├── __init__.py
│       │   ├── conftest.py
│       │   ├── README.md
│       │   ├── test_access_analyzer_fix.py
│       │   ├── test_network_security_additional.py
│       │   ├── test_network_security.py
│       │   ├── test_prompt_utils_coverage.py
│       │   ├── test_prompt_utils.py
│       │   ├── test_resource_utils_fix.py
│       │   ├── test_resource_utils.py
│       │   ├── test_security_services_additional.py
│       │   ├── test_security_services_coverage.py
│       │   ├── test_security_services.py
│       │   ├── test_server_additional.py
│       │   ├── test_server_coverage.py
│       │   ├── test_server_prompts.py
│       │   ├── test_server_security_findings.py
│       │   ├── test_server.py
│       │   ├── test_storage_security_additional.py
│       │   ├── test_storage_security_comprehensive.py
│       │   ├── test_storage_security_edge_cases.py
│       │   ├── test_storage_security_recommendations.py
│       │   ├── test_storage_security.py
│       │   └── test_user_agent_config.py
│       └── uv.lock
└── VIBE_CODING_TIPS_TRICKS.md
```

# Files

--------------------------------------------------------------------------------
/src/eks-mcp-server/tests/test_k8s_handler.py:
--------------------------------------------------------------------------------

```python
   1 | # Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
   2 | #
   3 | # Licensed under the Apache License, Version 2.0 (the "License");
   4 | # you may not use this file except in compliance with the License.
   5 | # You may obtain a copy of the License at
   6 | #
   7 | #     http://www.apache.org/licenses/LICENSE-2.0
   8 | #
   9 | # Unless required by applicable law or agreed to in writing, software
  10 | # distributed under the License is distributed on an "AS IS" BASIS,
  11 | # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12 | # See the License for the specific language governing permissions and
  13 | # limitations under the License.
  14 | # ruff: noqa: D101, D102, D103
  15 | """Tests for the K8sHandler class."""
  16 | 
  17 | import os
  18 | import pytest
  19 | from awslabs.eks_mcp_server.k8s_apis import K8sApis
  20 | from awslabs.eks_mcp_server.k8s_handler import K8sHandler
  21 | from mcp.server.fastmcp import Context
  22 | from mcp.types import TextContent
  23 | from unittest.mock import MagicMock, mock_open, patch
  24 | 
  25 | 
  26 | @pytest.fixture
  27 | def mock_context():
  28 |     """Create a mock MCP context."""
  29 |     ctx = MagicMock(spec=Context)
  30 |     ctx.request_id = 'test-request-id'
  31 |     return ctx
  32 | 
  33 | 
  34 | @pytest.fixture
  35 | def mock_mcp():
  36 |     """Create a mock MCP server."""
  37 |     return MagicMock()
  38 | 
  39 | 
  40 | @pytest.fixture
  41 | def mock_client_cache():
  42 |     """Create a mock K8sClientCache."""
  43 |     cache = MagicMock()
  44 |     mock_k8s_apis = MagicMock(spec=K8sApis)
  45 |     cache.get_client.return_value = mock_k8s_apis
  46 |     return cache
  47 | 
  48 | 
  49 | @pytest.fixture
  50 | def mock_k8s_apis():
  51 |     """Create a mock K8sApis instance."""
  52 |     return MagicMock(spec=K8sApis)
  53 | 
  54 | 
  55 | class TestK8sHandler:
  56 |     """Tests for the K8sHandler class."""
  57 | 
  58 |     def test_init(self, mock_mcp, mock_client_cache):
  59 |         """Test initialization of K8sHandler."""
  60 |         # Initialize the K8s handler with allow_write=True
  61 |         with patch(
  62 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
  63 |         ):
  64 |             handler = K8sHandler(mock_mcp, allow_write=True)
  65 | 
  66 |             # Verify that the handler has the correct attributes
  67 |             assert handler.mcp == mock_mcp
  68 |             assert handler.client_cache == mock_client_cache
  69 |             assert handler.allow_write is True
  70 |             assert handler.allow_sensitive_data_access is False
  71 | 
  72 |         # Verify that the tools were registered
  73 |         assert mock_mcp.tool.call_count == 7
  74 | 
  75 |         # Get all call args
  76 |         call_args_list = mock_mcp.tool.call_args_list
  77 | 
  78 |         # Get all tool names that were registered
  79 |         tool_names = [call_args[1]['name'] for call_args in call_args_list]
  80 | 
  81 |         # Verify that expected tools were registered
  82 |         assert 'list_k8s_resources' in tool_names
  83 |         assert 'generate_app_manifest' in tool_names
  84 |         assert 'apply_yaml' in tool_names
  85 |         assert 'manage_k8s_resource' in tool_names
  86 |         assert 'get_pod_logs' in tool_names
  87 |         assert 'get_k8s_events' in tool_names
  88 | 
  89 |     def test_init_with_sensitive_data_access(self, mock_mcp, mock_client_cache):
  90 |         """Test initialization of K8sHandler with sensitive data access enabled."""
  91 |         # Initialize the K8s handler with sensitive data access enabled
  92 |         with patch(
  93 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
  94 |         ):
  95 |             handler = K8sHandler(mock_mcp, allow_write=False, allow_sensitive_data_access=True)
  96 | 
  97 |             # Verify that the handler has the correct attributes
  98 |             assert handler.mcp == mock_mcp
  99 |             assert handler.client_cache == mock_client_cache
 100 |             assert handler.allow_write is False
 101 |             assert handler.allow_sensitive_data_access is True
 102 | 
 103 |         # Verify that the tools were registered
 104 |         assert mock_mcp.tool.call_count == 7
 105 | 
 106 |         # Get all call args
 107 |         call_args_list = mock_mcp.tool.call_args_list
 108 | 
 109 |         # Get all tool names that were registered
 110 |         tool_names = [call_args[1]['name'] for call_args in call_args_list]
 111 | 
 112 |         # Verify that expected tools were registered
 113 |         assert 'list_k8s_resources' in tool_names
 114 |         assert 'get_pod_logs' in tool_names
 115 |         assert 'get_k8s_events' in tool_names
 116 |         assert 'list_api_versions' in tool_names
 117 |         assert 'manage_k8s_resource' in tool_names
 118 |         assert 'apply_yaml' in tool_names
 119 |         assert 'generate_app_manifest' in tool_names
 120 | 
 121 |     def test_get_client(self, mock_mcp, mock_client_cache):
 122 |         """Test get_client method delegates to the client cache."""
 123 |         # Initialize the K8s handler
 124 |         with patch(
 125 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 126 |         ):
 127 |             handler = K8sHandler(mock_mcp)
 128 | 
 129 |             # Get a client
 130 |             client = handler.get_client('test-cluster')
 131 | 
 132 |             # Verify that get_client was called on the cache
 133 |             mock_client_cache.get_client.assert_called_once_with('test-cluster')
 134 | 
 135 |             # Verify that the client was returned
 136 |             assert client == mock_client_cache.get_client.return_value
 137 | 
 138 |     def test_load_yaml_template_removes_checkov_annotations(self, mock_mcp, mock_client_cache):
 139 |         """Test _load_yaml_template method removes checkov skip annotations from deployment template."""
 140 |         # Initialize the K8s handler
 141 |         with patch(
 142 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 143 |         ):
 144 |             handler = K8sHandler(mock_mcp)
 145 | 
 146 |         # Create mock file content for templates with checkov skip annotations
 147 |         deployment_template = """apiVersion: apps/v1
 148 | kind: Deployment
 149 | metadata:
 150 |   name: APP_NAME
 151 |   namespace: NAMESPACE
 152 |   annotations:
 153 |     checkov.io/skip1: "CKV_K8S_14=We're using a specific image version"
 154 |     checkov.io/skip2: "CKV_K8S_43=Resource limits are set appropriately"
 155 |     other-annotation: "This should be preserved"
 156 | spec:
 157 |   replicas: REPLICAS"""
 158 | 
 159 |         service_template = """apiVersion: v1
 160 | kind: Service
 161 | metadata:
 162 |   name: APP_NAME
 163 |   namespace: NAMESPACE
 164 |   annotations:
 165 |     service.beta.kubernetes.io/aws-load-balancer-scheme: LOAD_BALANCER_SCHEME"""
 166 | 
 167 |         # Mock open to return our test templates
 168 |         mock_open_func = mock_open()
 169 |         mock_file = MagicMock()
 170 |         mock_file.__enter__.return_value.read.side_effect = [deployment_template, service_template]
 171 |         mock_open_func.return_value = mock_file
 172 | 
 173 |         # Mock yaml.safe_load and yaml.dump to use real functions
 174 |         with patch('builtins.open', mock_open_func):
 175 |             # Test loading and processing templates
 176 |             template_files = ['deployment.yaml', 'service.yaml']
 177 |             values = {
 178 |                 'APP_NAME': 'test-app',
 179 |                 'NAMESPACE': 'test-namespace',
 180 |                 'REPLICAS': '3',
 181 |                 'LOAD_BALANCER_SCHEME': 'internal',
 182 |             }
 183 | 
 184 |             result = handler._load_yaml_template(template_files, values)
 185 | 
 186 |             # Verify open was called for each template
 187 |             assert mock_open_func.call_count == 2
 188 | 
 189 |             # Verify template content was properly processed
 190 |             assert 'kind: Deployment' in result
 191 |             assert 'kind: Service' in result
 192 |             assert 'name: test-app' in result
 193 |             assert 'namespace: test-namespace' in result
 194 |             assert 'replicas: 3' in result
 195 |             assert 'service.beta.kubernetes.io/aws-load-balancer-scheme: internal' in result
 196 | 
 197 |             # Verify checkov annotations were removed
 198 |             assert 'checkov.io/skip1' not in result
 199 |             assert 'checkov.io/skip2' not in result
 200 | 
 201 |             # Verify other annotations were preserved
 202 |             assert 'other-annotation: This should be preserved' in result
 203 | 
 204 |     @pytest.mark.asyncio
 205 |     async def test_apply_yaml_relative_path(self, mock_context, mock_mcp, mock_client_cache):
 206 |         """Test apply_yaml method with a relative path."""
 207 |         # Initialize the K8s handler
 208 |         with patch(
 209 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 210 |         ):
 211 |             handler = K8sHandler(mock_mcp)
 212 | 
 213 |         # Mock os.path.isabs to return False for relative paths
 214 |         with patch('os.path.isabs', return_value=False):
 215 |             # Apply YAML from a relative path
 216 |             result = await handler.apply_yaml(
 217 |                 mock_context,
 218 |                 yaml_path='relative/path/to/manifest.yaml',
 219 |                 cluster_name='test-cluster',
 220 |                 namespace='default',
 221 |                 force=True,
 222 |             )
 223 | 
 224 |             # Verify the result
 225 |             assert result.isError
 226 |             assert isinstance(result.content[0], TextContent)
 227 |             assert 'Path must be absolute' in result.content[0].text
 228 |             assert 'relative/path/to/manifest.yaml' in result.content[0].text
 229 | 
 230 |     @pytest.mark.asyncio
 231 |     async def test_apply_yaml_success(self, mock_context, mock_mcp, mock_client_cache):
 232 |         """Test apply_yaml method with successful application."""
 233 |         # Initialize the K8s handler
 234 |         with patch(
 235 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 236 |         ):
 237 |             handler = K8sHandler(mock_mcp)
 238 | 
 239 |         # Mock get_client
 240 |         mock_k8s_apis = MagicMock()
 241 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis) as mock_client:
 242 |             # Mock os.path.isabs to return True for absolute paths
 243 |             with patch('os.path.isabs', return_value=True):
 244 |                 # Mock open to read the YAML file
 245 |                 yaml_content = """apiVersion: v1
 246 | kind: Namespace
 247 | metadata:
 248 |   name: test-namespace
 249 | """
 250 |                 with patch('builtins.open', mock_open(read_data=yaml_content)) as mocked_open:
 251 |                     # Mock apply_from_yaml
 252 |                     mock_k8s_apis.apply_from_yaml.return_value = ([], 1, 0)
 253 | 
 254 |                     # Apply YAML from file
 255 |                     result = await handler.apply_yaml(
 256 |                         mock_context,
 257 |                         yaml_path='/path/to/manifest.yaml',
 258 |                         cluster_name='test-cluster',
 259 |                         namespace='default',
 260 |                         force=True,
 261 |                     )
 262 | 
 263 |                     # Verify that get_client was called
 264 |                     mock_client.assert_called_once_with('test-cluster')
 265 | 
 266 |                     # Verify that open was called with the correct path
 267 |                     mocked_open.assert_called_once_with('/path/to/manifest.yaml', 'r')
 268 | 
 269 |                     # Verify that apply_from_yaml was called with the correct parameters
 270 |                     mock_k8s_apis.apply_from_yaml.assert_called_once()
 271 |                     args, kwargs = mock_k8s_apis.apply_from_yaml.call_args
 272 |                     assert len(kwargs['yaml_objects']) == 1
 273 |                     assert kwargs['yaml_objects'][0]['kind'] == 'Namespace'
 274 |                     assert kwargs['namespace'] == 'default'
 275 |                     assert kwargs['force'] is True
 276 | 
 277 |                     # Verify the result
 278 |                     assert not result.isError
 279 |                     assert isinstance(result.content[0], TextContent)
 280 |                     assert (
 281 |                         'Successfully applied all resources from YAML file'
 282 |                         in result.content[0].text
 283 |                     )
 284 | 
 285 |     @pytest.mark.asyncio
 286 |     async def test_apply_yaml_file_not_found(self, mock_context, mock_mcp, mock_client_cache):
 287 |         """Test apply_yaml method with file not found error."""
 288 |         # Initialize the K8s handler
 289 |         with patch(
 290 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 291 |         ):
 292 |             handler = K8sHandler(mock_mcp)
 293 | 
 294 |         # Mock get_client
 295 |         mock_k8s_apis = MagicMock()
 296 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis) as mock_client:
 297 |             # Mock os.path.isabs to return True for absolute paths
 298 |             with patch('os.path.isabs', return_value=True):
 299 |                 # Mock open to raise FileNotFoundError
 300 |                 with patch('builtins.open', side_effect=FileNotFoundError()):
 301 |                     # Apply YAML from file
 302 |                     result = await handler.apply_yaml(
 303 |                         mock_context,
 304 |                         yaml_path='/path/to/nonexistent.yaml',
 305 |                         cluster_name='test-cluster',
 306 |                         namespace='default',
 307 |                         force=True,
 308 |                     )
 309 | 
 310 |                     # Verify that get_client was called
 311 |                     mock_client.assert_called_once_with('test-cluster')
 312 | 
 313 |                     # Verify the result
 314 |                     assert result.isError
 315 |                     assert isinstance(result.content[0], TextContent)
 316 |                     assert 'YAML file not found' in result.content[0].text
 317 | 
 318 |     @pytest.mark.asyncio
 319 |     async def test_apply_yaml_io_error(self, mock_context, mock_mcp, mock_client_cache):
 320 |         """Test apply_yaml method with IO error."""
 321 |         # Initialize the K8s handler
 322 |         with patch(
 323 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 324 |         ):
 325 |             handler = K8sHandler(mock_mcp)
 326 | 
 327 |         # Mock get_client
 328 |         mock_k8s_apis = MagicMock()
 329 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis) as mock_client:
 330 |             # Mock os.path.isabs to return True for absolute paths
 331 |             with patch('os.path.isabs', return_value=True):
 332 |                 # Mock open to raise IOError
 333 |                 with patch('builtins.open', side_effect=IOError('Permission denied')):
 334 |                     # Apply YAML from file
 335 |                     result = await handler.apply_yaml(
 336 |                         mock_context,
 337 |                         yaml_path='/path/to/protected.yaml',
 338 |                         cluster_name='test-cluster',
 339 |                         namespace='default',
 340 |                         force=True,
 341 |                     )
 342 | 
 343 |                     # Verify that get_client was called
 344 |                     mock_client.assert_called_once_with('test-cluster')
 345 | 
 346 |                     # Verify the result
 347 |                     assert result.isError
 348 |                     assert isinstance(result.content[0], TextContent)
 349 |                     assert 'Error reading YAML file' in result.content[0].text
 350 |                     assert 'Permission denied' in result.content[0].text
 351 | 
 352 |     @pytest.mark.asyncio
 353 |     async def test_apply_yaml_create_error(self, mock_context, mock_mcp, mock_client_cache):
 354 |         """Test apply_yaml method with error from create_from_yaml."""
 355 |         # Initialize the K8s handler
 356 |         with patch(
 357 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 358 |         ):
 359 |             handler = K8sHandler(mock_mcp)
 360 | 
 361 |         # Mock get_client
 362 |         mock_k8s_apis = MagicMock()
 363 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis):
 364 |             # Mock os.path.isabs to return True for absolute paths
 365 |             with patch('os.path.isabs', return_value=True):
 366 |                 # Mock open to read the YAML file
 367 |                 yaml_content = """apiVersion: v1
 368 | kind: Namespace
 369 | metadata:
 370 |   name: test-namespace
 371 | """
 372 |                 with patch('builtins.open', mock_open(read_data=yaml_content)):
 373 |                     # Mock apply_from_yaml to raise an exception
 374 |                     mock_k8s_apis.apply_from_yaml.side_effect = Exception(
 375 |                         'Failed to create resource'
 376 |                     )
 377 | 
 378 |                     # Apply YAML from file
 379 |                     result = await handler.apply_yaml(
 380 |                         mock_context,
 381 |                         yaml_path='/path/to/manifest.yaml',
 382 |                         cluster_name='test-cluster',
 383 |                         namespace='default',
 384 |                         force=True,
 385 |                     )
 386 | 
 387 |                     # Verify the result
 388 |                     assert result.isError
 389 |                     assert isinstance(result.content[0], TextContent)
 390 |                     assert 'Failed to apply YAML from file' in result.content[0].text
 391 |                     assert 'Failed to create resource' in result.content[0].text
 392 | 
 393 |     # Note: TTL cache expiration tests have been moved to test_k8s_client_cache.py
 394 | 
 395 |     @pytest.mark.asyncio
 396 |     async def test_manage_k8s_resource_create(self, mock_context, mock_mcp, mock_client_cache):
 397 |         """Test manage_k8s_resource method with create operation."""
 398 |         # Initialize the K8s handler
 399 |         with patch(
 400 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 401 |         ):
 402 |             handler = K8sHandler(mock_mcp, allow_write=True)
 403 | 
 404 |         # Mock the get_client method and k8s_apis.manage_resource
 405 |         mock_k8s_apis = MagicMock()
 406 |         mock_response = MagicMock()
 407 |         mock_response.to_dict.return_value = {
 408 |             'kind': 'Pod',
 409 |             'apiVersion': 'v1',
 410 |             'metadata': {'name': 'test-pod', 'namespace': 'test-namespace'},
 411 |         }
 412 |         mock_k8s_apis.manage_resource.return_value = mock_response
 413 | 
 414 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis) as mock_client:
 415 |             # Create a test resource
 416 |             body = {
 417 |                 'metadata': {'name': 'test-pod'},
 418 |                 'spec': {'containers': [{'name': 'test-container', 'image': 'nginx'}]},
 419 |             }
 420 | 
 421 |             result = await handler.manage_k8s_resource(
 422 |                 mock_context,
 423 |                 operation='create',
 424 |                 cluster_name='test-cluster',
 425 |                 kind='Pod',
 426 |                 api_version='v1',
 427 |                 name='test-pod',
 428 |                 namespace='test-namespace',
 429 |                 body=body,
 430 |             )
 431 | 
 432 |             # Verify that get_client was called
 433 |             mock_client.assert_called_once_with('test-cluster')
 434 | 
 435 |             # Verify that manage_resource was called with the correct parameters
 436 |             mock_k8s_apis.manage_resource.assert_called_once()
 437 | 
 438 |             # Verify the result
 439 |             assert not result.isError
 440 |             assert result.kind == 'Pod'
 441 |             assert result.name == 'test-pod'
 442 |             assert result.namespace == 'test-namespace'
 443 |             assert result.api_version == 'v1'
 444 |             assert result.operation == 'create'
 445 |             assert isinstance(result.content[0], TextContent)
 446 |             assert 'Successfully created Pod test-namespace/test-pod' in result.content[0].text
 447 | 
 448 |     @pytest.mark.asyncio
 449 |     async def test_read_k8s_resource(self, mock_context, mock_mcp, mock_client_cache):
 450 |         """Test read_k8s_resource method."""
 451 |         # Initialize the K8s handler
 452 |         with patch(
 453 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 454 |         ):
 455 |             handler = K8sHandler(mock_mcp)
 456 | 
 457 |         # Mock the get_client method and k8s_apis.manage_resource
 458 |         mock_k8s_apis = MagicMock()
 459 |         mock_response = MagicMock()
 460 |         mock_response.to_dict.return_value = {
 461 |             'kind': 'Pod',
 462 |             'apiVersion': 'v1',
 463 |             'metadata': {'name': 'test-pod', 'namespace': 'test-namespace'},
 464 |         }
 465 |         mock_k8s_apis.manage_resource.return_value = mock_response
 466 | 
 467 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis):
 468 |             result = await handler.manage_k8s_resource(
 469 |                 mock_context,
 470 |                 operation='read',
 471 |                 cluster_name='test-cluster',
 472 |                 kind='Pod',
 473 |                 api_version='v1',
 474 |                 name='test-pod',
 475 |                 namespace='test-namespace',
 476 |             )
 477 | 
 478 |             # Verify the result
 479 |             assert not result.isError
 480 |             assert result.kind == 'Pod'
 481 |             assert result.name == 'test-pod'
 482 |             assert result.namespace == 'test-namespace'
 483 |             assert result.api_version == 'v1'
 484 |             assert result.operation == 'read'
 485 |             assert result.resource is not None
 486 |             assert isinstance(result.content[0], TextContent)
 487 |             assert 'Successfully retrieved Pod test-namespace/test-pod' in result.content[0].text
 488 | 
 489 |     @pytest.mark.asyncio
 490 |     async def test_manage_k8s_resource_invalid_operation(
 491 |         self, mock_context, mock_mcp, mock_client_cache
 492 |     ):
 493 |         """Test manage_k8s_resource method with an invalid operation."""
 494 |         # Initialize the K8s handler
 495 |         with patch(
 496 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 497 |         ):
 498 |             handler = K8sHandler(mock_mcp)
 499 | 
 500 |         # Call manage_k8s_resource with an invalid operation
 501 |         result = await handler.manage_k8s_resource(
 502 |             mock_context,
 503 |             operation='invalid',
 504 |             cluster_name='test-cluster',
 505 |             kind='Pod',
 506 |             api_version='v1',
 507 |             name='test-pod',
 508 |             namespace='test-namespace',
 509 |         )
 510 | 
 511 |         # Verify the result
 512 |         assert result.isError
 513 |         assert result.kind == 'Pod'
 514 |         assert result.name == 'test-pod'
 515 |         assert result.namespace == 'test-namespace'
 516 |         assert result.api_version == 'v1'
 517 |         assert result.operation == 'invalid'
 518 |         assert isinstance(result.content[0], TextContent)
 519 |         assert 'Invalid operation: invalid' in result.content[0].text
 520 | 
 521 |     @pytest.mark.asyncio
 522 |     async def test_manage_k8s_resource_error(self, mock_context, mock_mcp, mock_client_cache):
 523 |         """Test manage_k8s_resource method with an error."""
 524 |         # Initialize the K8s handler
 525 |         with patch(
 526 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 527 |         ):
 528 |             handler = K8sHandler(mock_mcp)
 529 | 
 530 |         # Mock get_client
 531 |         mock_k8s_apis = MagicMock()
 532 |         mock_k8s_apis.manage_resource.side_effect = Exception('Resource not found')
 533 | 
 534 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis) as mock_client:
 535 |             result = await handler.manage_k8s_resource(
 536 |                 mock_context,
 537 |                 operation='read',
 538 |                 cluster_name='test-cluster',
 539 |                 kind='Pod',
 540 |                 api_version='v1',
 541 |                 name='test-pod',
 542 |                 namespace='test-namespace',
 543 |             )
 544 | 
 545 |             # Verify that get_client was called
 546 |             mock_client.assert_called_once_with('test-cluster')
 547 | 
 548 |             # Verify that manage_resource was called with the correct parameters
 549 |             mock_k8s_apis.manage_resource.assert_called_once()
 550 | 
 551 |             # Verify the result
 552 |             assert result.isError
 553 |             assert result.kind == 'Pod'
 554 |             assert result.name == 'test-pod'
 555 |             assert result.namespace == 'test-namespace'
 556 |             assert result.api_version == 'v1'
 557 |             assert result.operation == 'read'
 558 |             assert isinstance(result.content[0], TextContent)
 559 |             assert (
 560 |                 'Failed to read Pod test-namespace/test-pod: Resource not found'
 561 |                 in result.content[0].text
 562 |             )
 563 | 
 564 |     @pytest.mark.asyncio
 565 |     async def test_manage_k8s_resource_secret_sensitive_data_access_disabled(
 566 |         self, mock_context, mock_mcp, mock_client_cache
 567 |     ):
 568 |         """Test manage_k8s_resource method with Secret kind and sensitive data access disabled."""
 569 |         # Initialize the K8s handler with sensitive data access disabled but write access enabled
 570 |         with patch(
 571 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 572 |         ):
 573 |             handler = K8sHandler(mock_mcp, allow_write=True, allow_sensitive_data_access=False)
 574 | 
 575 |         # Test with read operation on Secret (should be rejected)
 576 |         result = await handler.manage_k8s_resource(
 577 |             mock_context,
 578 |             operation='read',
 579 |             cluster_name='test-cluster',
 580 |             kind='Secret',
 581 |             api_version='v1',
 582 |             name='test-secret',
 583 |             namespace='test-namespace',
 584 |         )
 585 | 
 586 |         # Verify the result
 587 |         assert result.isError
 588 |         assert result.kind == 'Secret'
 589 |         assert result.name == 'test-secret'
 590 |         assert result.namespace == 'test-namespace'
 591 |         assert result.api_version == 'v1'
 592 |         assert result.operation == 'read'
 593 |         assert isinstance(result.content[0], TextContent)
 594 |         assert (
 595 |             'Access to Kubernetes Secrets requires --allow-sensitive-data-access flag'
 596 |             in result.content[0].text
 597 |         )
 598 | 
 599 |         # Test with create operation on Secret (should be rejected for sensitive data access, not write access)
 600 |         result = await handler.manage_k8s_resource(
 601 |             mock_context,
 602 |             operation='create',
 603 |             cluster_name='test-cluster',
 604 |             kind='Secret',
 605 |             api_version='v1',
 606 |             name='test-secret',
 607 |             namespace='test-namespace',
 608 |             body={'metadata': {'name': 'test-secret'}, 'data': {'key': 'dmFsdWU='}},
 609 |         )
 610 | 
 611 |         # Verify the result
 612 |         assert not result.isError
 613 |         assert result.kind == 'Secret'
 614 |         assert result.name == 'test-secret'
 615 |         assert result.namespace == 'test-namespace'
 616 |         assert result.api_version == 'v1'
 617 |         assert result.operation == 'create'
 618 |         assert isinstance(result.content[0], TextContent)
 619 | 
 620 |     @pytest.mark.asyncio
 621 |     async def test_manage_k8s_resource_write_access_disabled(
 622 |         self, mock_context, mock_mcp, mock_client_cache
 623 |     ):
 624 |         """Test manage_k8s_resource method with write access disabled for mutable operations."""
 625 |         # Initialize the K8s handler with write access disabled
 626 |         with patch(
 627 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 628 |         ):
 629 |             handler = K8sHandler(mock_mcp, allow_write=False)
 630 | 
 631 |         # Test with create operation (should be rejected)
 632 |         result = await handler.manage_k8s_resource(
 633 |             mock_context,
 634 |             operation='create',
 635 |             cluster_name='test-cluster',
 636 |             kind='Pod',
 637 |             api_version='v1',
 638 |             name='test-pod',
 639 |             namespace='test-namespace',
 640 |             body={'metadata': {'name': 'test-pod'}},
 641 |         )
 642 | 
 643 |         # Verify the result
 644 |         assert result.isError
 645 |         assert result.kind == 'Pod'
 646 |         assert result.name == 'test-pod'
 647 |         assert result.namespace == 'test-namespace'
 648 |         assert result.api_version == 'v1'
 649 |         assert result.operation == 'create'
 650 |         assert isinstance(result.content[0], TextContent)
 651 |         assert 'Operation create is not allowed without write access' in result.content[0].text
 652 | 
 653 |         # Test with replace operation (should be rejected when write access is disabled)
 654 |         result = await handler.manage_k8s_resource(
 655 |             mock_context,
 656 |             operation='replace',
 657 |             cluster_name='test-cluster',
 658 |             kind='Pod',
 659 |             api_version='v1',
 660 |             name='test-pod',
 661 |             namespace='test-namespace',
 662 |             body={'metadata': {'name': 'test-pod'}},
 663 |         )
 664 | 
 665 |         # Verify the result
 666 |         assert result.isError
 667 |         assert result.operation == 'replace'
 668 |         assert isinstance(result.content[0], TextContent)
 669 |         assert 'Operation replace is not allowed without write access' in result.content[0].text
 670 | 
 671 |         # Test with patch operation (should be rejected when write access is disabled)
 672 |         result = await handler.manage_k8s_resource(
 673 |             mock_context,
 674 |             operation='patch',
 675 |             cluster_name='test-cluster',
 676 |             kind='Pod',
 677 |             api_version='v1',
 678 |             name='test-pod',
 679 |             namespace='test-namespace',
 680 |             body={'metadata': {'labels': {'app': 'test'}}},
 681 |         )
 682 | 
 683 |         # Verify the result
 684 |         assert result.isError
 685 |         assert result.operation == 'patch'
 686 |         assert isinstance(result.content[0], TextContent)
 687 |         assert 'Operation patch is not allowed without write access' in result.content[0].text
 688 | 
 689 |         # Test with delete operation (should be rejected when write access is disabled)
 690 |         result = await handler.manage_k8s_resource(
 691 |             mock_context,
 692 |             operation='delete',
 693 |             cluster_name='test-cluster',
 694 |             kind='Pod',
 695 |             api_version='v1',
 696 |             name='test-pod',
 697 |             namespace='test-namespace',
 698 |         )
 699 | 
 700 |         # Verify the result
 701 |         assert result.isError
 702 |         assert result.operation == 'delete'
 703 |         assert isinstance(result.content[0], TextContent)
 704 |         assert 'Operation delete is not allowed without write access' in result.content[0].text
 705 | 
 706 |         # Test with read operation (should be allowed even when write access is disabled)
 707 |         mock_k8s_apis = MagicMock()
 708 |         mock_response = MagicMock()
 709 |         mock_response.to_dict.return_value = {
 710 |             'kind': 'Pod',
 711 |             'apiVersion': 'v1',
 712 |             'metadata': {'name': 'test-pod', 'namespace': 'test-namespace'},
 713 |         }
 714 |         mock_k8s_apis.manage_resource.return_value = mock_response
 715 | 
 716 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis) as mock_client:
 717 |             result = await handler.manage_k8s_resource(
 718 |                 mock_context,
 719 |                 operation='read',
 720 |                 cluster_name='test-cluster',
 721 |                 kind='Pod',
 722 |                 api_version='v1',
 723 |                 name='test-pod',
 724 |                 namespace='test-namespace',
 725 |             )
 726 | 
 727 |             # Verify that get_client was called
 728 |             mock_client.assert_called_once_with('test-cluster')
 729 | 
 730 |             # Verify that manage_resource was called
 731 |             mock_k8s_apis.manage_resource.assert_called_once()
 732 | 
 733 |             # Verify the result
 734 |             assert not result.isError
 735 |             assert result.kind == 'Pod'
 736 |             assert result.name == 'test-pod'
 737 |             assert result.namespace == 'test-namespace'
 738 |             assert result.api_version == 'v1'
 739 |             assert result.operation == 'read'
 740 |             assert isinstance(result.content[0], TextContent)
 741 |             assert 'Successfully retrieved Pod test-namespace/test-pod' in result.content[0].text
 742 | 
 743 |     @pytest.mark.asyncio
 744 |     async def test_list_k8s_resources_success(self, mock_context, mock_mcp, mock_client_cache):
 745 |         """Test list_k8s_resources method with successful listing."""
 746 |         # Initialize the K8s handler
 747 |         with patch(
 748 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 749 |         ):
 750 |             handler = K8sHandler(mock_mcp)
 751 | 
 752 |         # Mock get_client
 753 |         mock_k8s_apis = MagicMock()
 754 | 
 755 |         # Mock response with items
 756 |         mock_item1 = MagicMock()
 757 |         mock_item1.to_dict.return_value = {
 758 |             'metadata': {
 759 |                 'name': 'test-pod-1',
 760 |                 'namespace': 'test-namespace',
 761 |                 'creation_timestamp': '2023-01-01T00:00:00Z',
 762 |                 'labels': {'app': 'test'},
 763 |                 'annotations': {'description': 'Test pod 1'},
 764 |             }
 765 |         }
 766 |         mock_item2 = MagicMock()
 767 |         mock_item2.to_dict.return_value = {
 768 |             'metadata': {
 769 |                 'name': 'test-pod-2',
 770 |                 'namespace': 'test-namespace',
 771 |                 'creation_timestamp': '2023-01-02T00:00:00Z',
 772 |                 'labels': {'app': 'test'},
 773 |                 'annotations': {'description': 'Test pod 2'},
 774 |             }
 775 |         }
 776 | 
 777 |         mock_response = MagicMock()
 778 |         mock_response.items = [mock_item1, mock_item2]
 779 |         mock_k8s_apis.list_resources.return_value = mock_response
 780 | 
 781 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis) as mock_client:
 782 |             result = await handler.list_k8s_resources(
 783 |                 mock_context,
 784 |                 cluster_name='test-cluster',
 785 |                 kind='Pod',
 786 |                 api_version='v1',
 787 |                 namespace='test-namespace',
 788 |                 label_selector='app=test',
 789 |             )
 790 | 
 791 |             # Verify that get_client was called
 792 |             mock_client.assert_called_once_with('test-cluster')
 793 | 
 794 |             # Verify that list_resources was called once
 795 |             mock_k8s_apis.list_resources.assert_called_once()
 796 | 
 797 |             # Get the call args
 798 |             args, kwargs = mock_k8s_apis.list_resources.call_args
 799 | 
 800 |             # Verify the positional args
 801 |             assert args[0] == 'Pod'
 802 |             assert args[1] == 'v1'
 803 | 
 804 |             # Verify the keyword args
 805 |             assert kwargs['namespace'] == 'test-namespace'
 806 |             assert kwargs['label_selector'] == 'app=test'
 807 | 
 808 |             # Verify the result
 809 |             assert not result.isError
 810 |             assert result.kind == 'Pod'
 811 |             assert result.api_version == 'v1'
 812 |             assert result.namespace == 'test-namespace'
 813 |             assert result.count == 2
 814 |             assert len(result.items) == 2
 815 |             assert result.items[0].name == 'test-pod-1'
 816 |             assert result.items[0].namespace == 'test-namespace'
 817 |             # Don't check creation_timestamp as it might be None in the actual implementation
 818 |             assert result.items[0].labels == {'app': 'test'}
 819 |             assert result.items[0].annotations == {'description': 'Test pod 1'}
 820 |             assert result.items[1].name == 'test-pod-2'
 821 |             assert isinstance(result.content[0], TextContent)
 822 |             assert (
 823 |                 'Successfully listed 2 Pod resources in test-namespace/' in result.content[0].text
 824 |             )
 825 | 
 826 |     @pytest.mark.asyncio
 827 |     async def test_list_k8s_resources_empty(self, mock_context, mock_mcp, mock_client_cache):
 828 |         """Test list_k8s_resources method with empty result."""
 829 |         # Initialize the K8s handler
 830 |         with patch(
 831 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 832 |         ):
 833 |             handler = K8sHandler(mock_mcp)
 834 | 
 835 |         # Mock get_client
 836 |         mock_k8s_apis = MagicMock()
 837 | 
 838 |         # Mock response with no items
 839 |         mock_response = MagicMock()
 840 |         mock_response.items = []
 841 |         mock_k8s_apis.list_resources.return_value = mock_response
 842 | 
 843 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis):
 844 |             result = await handler.list_k8s_resources(
 845 |                 mock_context,
 846 |                 cluster_name='test-cluster',
 847 |                 kind='Pod',
 848 |                 api_version='v1',
 849 |                 namespace='test-namespace',
 850 |             )
 851 | 
 852 |             # Verify the result
 853 |             assert not result.isError
 854 |             assert result.kind == 'Pod'
 855 |             assert result.count == 0
 856 |             assert len(result.items) == 0
 857 |             assert isinstance(result.content[0], TextContent)
 858 |             assert (
 859 |                 'Successfully listed 0 Pod resources in test-namespace/' in result.content[0].text
 860 |             )
 861 | 
 862 |     @pytest.mark.asyncio
 863 |     async def test_list_k8s_resources_error(self, mock_context, mock_mcp, mock_client_cache):
 864 |         """Test list_k8s_resources method with an error."""
 865 |         # Initialize the K8s handler
 866 |         with patch(
 867 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 868 |         ):
 869 |             handler = K8sHandler(mock_mcp)
 870 | 
 871 |         # Mock get_client
 872 |         mock_k8s_apis = MagicMock()
 873 |         mock_k8s_apis.list_resources.side_effect = Exception('Failed to list resources')
 874 | 
 875 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis):
 876 |             result = await handler.list_k8s_resources(
 877 |                 mock_context,
 878 |                 cluster_name='test-cluster',
 879 |                 kind='Pod',
 880 |                 api_version='v1',
 881 |                 namespace='test-namespace',
 882 |             )
 883 | 
 884 |             # Verify the result
 885 |             assert result.isError
 886 |             assert result.kind == 'Pod'
 887 |             assert result.count == 0
 888 |             assert len(result.items) == 0
 889 |             assert isinstance(result.content[0], TextContent)
 890 |             assert (
 891 |                 'Failed to list Pod resources: Failed to list resources' in result.content[0].text
 892 |             )
 893 | 
 894 |     @pytest.mark.asyncio
 895 |     async def test_generate_app_manifest_write_access_disabled(
 896 |         self, mock_context, mock_mcp, mock_client_cache
 897 |     ):
 898 |         """Test generate_app_manifest method with write access disabled."""
 899 |         # Initialize the K8s handler with write access disabled
 900 |         with patch(
 901 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 902 |         ):
 903 |             handler = K8sHandler(mock_mcp, allow_write=False)
 904 | 
 905 |         # Generate manifest with write access disabled
 906 |         result = await handler.generate_app_manifest(
 907 |             mock_context,
 908 |             app_name='test-app',
 909 |             image_uri='123456789012.dkr.ecr.region.amazonaws.com/repo:tag',
 910 |             output_dir='/absolute/path/to/output',
 911 |         )
 912 | 
 913 |         # Verify the result
 914 |         assert result.isError
 915 |         assert isinstance(result.content[0], TextContent)
 916 |         assert (
 917 |             'Operation generate_app_manifest is not allowed without write access'
 918 |             in result.content[0].text
 919 |         )
 920 |         assert result.output_file_path == ''
 921 | 
 922 |     @pytest.mark.asyncio
 923 |     async def test_generate_app_manifest_relative_path(
 924 |         self, mock_context, mock_mcp, mock_client_cache
 925 |     ):
 926 |         """Test generate_app_manifest method with a relative path."""
 927 |         # Initialize the K8s handler with write access enabled
 928 |         with patch(
 929 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 930 |         ):
 931 |             handler = K8sHandler(mock_mcp, allow_write=True)
 932 | 
 933 |         # Mock os.path.isabs to return False for relative paths
 934 |         with patch('os.path.isabs', return_value=False):
 935 |             # Generate manifest with a relative path
 936 |             result = await handler.generate_app_manifest(
 937 |                 mock_context,
 938 |                 app_name='test-app',
 939 |                 image_uri='123456789012.dkr.ecr.region.amazonaws.com/repo:tag',
 940 |                 output_dir='relative/path/to/output',
 941 |             )
 942 | 
 943 |             # Verify the result
 944 |             assert result.isError
 945 |             assert isinstance(result.content[0], TextContent)
 946 |             assert 'Output directory path must be absolute' in result.content[0].text
 947 |             assert 'relative/path/to/output' in result.content[0].text
 948 | 
 949 |     @pytest.mark.asyncio
 950 |     async def test_generate_app_manifest_success(self, mock_context, mock_mcp, mock_client_cache):
 951 |         """Test generate_app_manifest with successful creation."""
 952 |         # Initialize the K8s handler with write access enabled
 953 |         with patch(
 954 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
 955 |         ):
 956 |             handler = K8sHandler(mock_mcp, allow_write=True)
 957 | 
 958 |         # Mock the _load_yaml_template method to avoid template loading issues
 959 |         with patch.object(handler, '_load_yaml_template', return_value='combined yaml content'):
 960 |             # Mock os.path.isabs to return True for absolute paths
 961 |             with patch('os.path.isabs', return_value=True):
 962 |                 # Mock os.makedirs to avoid creating directories
 963 |                 with patch('os.makedirs') as mock_makedirs:
 964 |                     # Mock open for writing output
 965 |                     with patch('builtins.open', mock_open()) as mocked_open:
 966 |                         # Mock os.path.abspath to return a predictable absolute path
 967 |                         with patch(
 968 |                             'os.path.abspath',
 969 |                             return_value='/absolute/path/test-output/test-app-manifest.yaml',
 970 |                         ):
 971 |                             # Generate the manifest
 972 |                             result = await handler.generate_app_manifest(
 973 |                                 mock_context,
 974 |                                 app_name='test-app',
 975 |                                 image_uri='123456789012.dkr.ecr.region.amazonaws.com/repo:tag',
 976 |                                 port=8080,
 977 |                                 replicas=3,
 978 |                                 cpu='250m',
 979 |                                 memory='256Mi',
 980 |                                 namespace='test-namespace',
 981 |                                 load_balancer_scheme='internet-facing',
 982 |                                 output_dir='/absolute/path/test-output',
 983 |                             )
 984 | 
 985 |                             # Verify that os.makedirs was called with exist_ok=True
 986 |                             mock_makedirs.assert_called_once_with(
 987 |                                 '/absolute/path/test-output', exist_ok=True
 988 |                             )
 989 | 
 990 |                             # Verify that open was called for writing output
 991 |                             mocked_open.assert_called_once_with(
 992 |                                 '/absolute/path/test-output/test-app-manifest.yaml', 'w'
 993 |                             )
 994 | 
 995 |                             # Verify the result
 996 |                             assert not result.isError
 997 |                             assert isinstance(result.content[0], TextContent)
 998 |                             assert (
 999 |                                 'Successfully generated YAML for test-app'
1000 |                                 in result.content[0].text
1001 |                             )
1002 |                             assert (
1003 |                                 'with image 123456789012.dkr.ecr.region.amazonaws.com/repo:tag'
1004 |                                 in result.content[0].text
1005 |                             )
1006 | 
1007 |                             # Verify that the output path is absolute
1008 |                             assert os.path.isabs(result.output_file_path)
1009 |                             assert (
1010 |                                 result.output_file_path
1011 |                                 == '/absolute/path/test-output/test-app-manifest.yaml'
1012 |                             )
1013 | 
1014 |     @pytest.mark.asyncio
1015 |     async def test_generate_app_manifest_error(self, mock_context, mock_mcp, mock_client_cache):
1016 |         """Test generate_app_manifest with an error."""
1017 |         # Initialize the K8s handler with write access enabled
1018 |         with patch(
1019 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1020 |         ):
1021 |             handler = K8sHandler(mock_mcp, allow_write=True)
1022 | 
1023 |         # Mock os.path.isabs to return True for absolute paths
1024 |         with patch('os.path.isabs', return_value=True):
1025 |             # Mock open function to raise an exception
1026 |             with patch('builtins.open', side_effect=Exception('File error')):
1027 |                 # Generate the manifest with an absolute path
1028 |                 result = await handler.generate_app_manifest(
1029 |                     mock_context,
1030 |                     app_name='test-app',
1031 |                     image_uri='123456789012.dkr.ecr.region.amazonaws.com/repo:tag',
1032 |                     output_dir='/absolute/path/to/output',  # Use an absolute path
1033 |                 )
1034 | 
1035 |                 # Verify the result
1036 |                 assert result.isError
1037 |                 assert isinstance(result.content[0], TextContent)
1038 |                 assert 'Failed to generate YAML' in result.content[0].text
1039 |                 assert 'File error' in result.content[0].text
1040 |                 assert result.output_file_path == ''
1041 | 
1042 |     def test_load_yaml_template(self, mock_mcp, mock_client_cache):
1043 |         """Test _load_yaml_template method."""
1044 |         # Initialize the K8s handler
1045 |         with patch(
1046 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1047 |         ):
1048 |             handler = K8sHandler(mock_mcp)
1049 | 
1050 |         # Create mock file content for templates
1051 |         template1 = 'kind: Deployment\nmetadata:\n  name: APP_NAME'
1052 |         template2 = 'kind: Service\nmetadata:\n  name: APP_NAME'
1053 | 
1054 |         # Mock open to return our test templates
1055 |         mock_open = MagicMock()
1056 |         mock_file = MagicMock()
1057 |         mock_file.__enter__.return_value.read.side_effect = [template1, template2]
1058 |         mock_open.return_value = mock_file
1059 | 
1060 |         with patch('builtins.open', mock_open):
1061 |             # Test loading and processing templates
1062 |             template_files = ['file1.yaml', 'file2.yaml']
1063 |             values = {'APP_NAME': 'test-app'}
1064 | 
1065 |             result = handler._load_yaml_template(template_files, values)
1066 | 
1067 |             # Verify open was called for each template
1068 |             assert mock_open.call_count == 2
1069 | 
1070 |             # Verify template content was properly processed
1071 |             assert 'kind: Deployment' in result
1072 |             assert 'kind: Service' in result
1073 |             assert 'name: test-app' in result
1074 |             assert '---' in result
1075 | 
1076 |     @pytest.mark.asyncio
1077 |     async def test_generate_app_manifest_with_absolute_path(
1078 |         self, mock_context, mock_mcp, mock_client_cache
1079 |     ):
1080 |         """Test generate_app_manifest with an absolute path."""
1081 |         # Initialize the K8s handler with write access enabled
1082 |         with patch(
1083 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1084 |         ):
1085 |             handler = K8sHandler(mock_mcp, allow_write=True)
1086 | 
1087 |         # Mock the _load_yaml_template method to avoid template loading issues
1088 |         with patch.object(handler, '_load_yaml_template', return_value='combined yaml content'):
1089 |             # Mock os.path.isabs to return True for absolute paths
1090 |             with patch('os.path.isabs', return_value=True):
1091 |                 # Mock os.makedirs to avoid creating directories
1092 |                 with patch('os.makedirs') as mock_makedirs:
1093 |                     # Mock open for writing output
1094 |                     with patch('builtins.open', mock_open()) as mocked_open:
1095 |                         # Mock os.path.abspath to return a predictable absolute path
1096 |                         with patch(
1097 |                             'os.path.abspath',
1098 |                             return_value='/path/to/output/test-app-manifest.yaml',
1099 |                         ):
1100 |                             # Generate the manifest with an absolute path
1101 |                             result = await handler.generate_app_manifest(
1102 |                                 mock_context,
1103 |                                 app_name='test-app',
1104 |                                 image_uri='123456789012.dkr.ecr.region.amazonaws.com/repo:tag',
1105 |                                 output_dir='/path/to/output',
1106 |                             )
1107 | 
1108 |                             # Verify that os.makedirs was called with exist_ok=True
1109 |                             mock_makedirs.assert_called_once_with('/path/to/output', exist_ok=True)
1110 | 
1111 |                             # Verify that open was called for writing output
1112 |                             mocked_open.assert_called_once_with(
1113 |                                 '/path/to/output/test-app-manifest.yaml', 'w'
1114 |                             )
1115 | 
1116 |                             # Verify the output file path is absolute
1117 |                             assert os.path.isabs(result.output_file_path)
1118 |                             assert (
1119 |                                 result.output_file_path == '/path/to/output/test-app-manifest.yaml'
1120 |                             )
1121 | 
1122 |                             # Verify the result is successful
1123 |                             assert not result.isError
1124 | 
1125 |     @pytest.mark.asyncio
1126 |     async def test_generate_app_manifest_multiple_templates(
1127 |         self, mock_context, mock_mcp, mock_client_cache
1128 |     ):
1129 |         """Test generate_app_manifest with multiple templates."""
1130 |         # Initialize the K8s handler with write access enabled
1131 |         with patch(
1132 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1133 |         ):
1134 |             handler = K8sHandler(mock_mcp, allow_write=True)
1135 | 
1136 |         # Mock the _load_yaml_template method to avoid template loading issues
1137 |         with patch.object(handler, '_load_yaml_template', return_value='combined yaml content'):
1138 |             # Mock os.path.isabs to return True for absolute paths
1139 |             with patch('os.path.isabs', return_value=True):
1140 |                 # Mock os.makedirs to avoid creating directories
1141 |                 with patch('os.makedirs') as mock_makedirs:
1142 |                     # Mock open for writing output
1143 |                     with patch('builtins.open', mock_open()) as mocked_open:
1144 |                         # Mock os.path.abspath to return a predictable absolute path
1145 |                         with patch(
1146 |                             'os.path.abspath',
1147 |                             return_value='/absolute/path/output/test-app-manifest.yaml',
1148 |                         ):
1149 |                             # Generate the manifest with all required parameters explicitly specified
1150 |                             result = await handler.generate_app_manifest(
1151 |                                 mock_context,
1152 |                                 app_name='test-app',
1153 |                                 image_uri='123456789012.dkr.ecr.region.amazonaws.com/repo:tag',
1154 |                                 port=80,
1155 |                                 replicas=2,
1156 |                                 cpu='100m',
1157 |                                 memory='128Mi',
1158 |                                 namespace='default',
1159 |                                 load_balancer_scheme='internal',  # Using the default value
1160 |                                 output_dir='/absolute/path/output',
1161 |                             )
1162 | 
1163 |                             # Verify that os.makedirs was called with exist_ok=True
1164 |                             mock_makedirs.assert_called_once_with(
1165 |                                 '/absolute/path/output', exist_ok=True
1166 |                             )
1167 | 
1168 |                             # Verify that open was called for writing output
1169 |                             mocked_open.assert_called_once_with(
1170 |                                 '/absolute/path/output/test-app-manifest.yaml', 'w'
1171 |                             )
1172 | 
1173 |                             # Verify the output file path is absolute
1174 |                             assert os.path.isabs(result.output_file_path)
1175 |                             assert (
1176 |                                 result.output_file_path
1177 |                                 == '/absolute/path/output/test-app-manifest.yaml'
1178 |                             )
1179 | 
1180 |                             # Verify the result is successful
1181 |                             assert not result.isError
1182 | 
1183 |     def test_init_with_get_pod_logs(self, mock_mcp, mock_client_cache):
1184 |         """Test initialization of K8sHandler with get_pod_logs tool."""
1185 |         # Initialize the K8s handler with both write and sensitive data access enabled
1186 |         with patch(
1187 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1188 |         ):
1189 |             K8sHandler(mock_mcp, allow_write=True, allow_sensitive_data_access=True)
1190 | 
1191 |         # Verify that the tools were registered
1192 |         assert mock_mcp.tool.call_count == 7
1193 | 
1194 |         # Get all call args
1195 |         call_args_list = mock_mcp.tool.call_args_list
1196 | 
1197 |         # Get all tool names that were registered
1198 |         tool_names = [call_args[1]['name'] for call_args in call_args_list]
1199 | 
1200 |         # Verify that get_pod_logs and get_k8s_events were registered
1201 |         assert 'get_pod_logs' in tool_names
1202 |         assert 'get_k8s_events' in tool_names
1203 | 
1204 |     def test_init_write_access_disabled(self, mock_mcp, mock_client_cache):
1205 |         """Test initialization of K8sHandler with write access disabled."""
1206 |         # Initialize the K8s handler with write access disabled but sensitive data access enabled
1207 |         with patch(
1208 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1209 |         ):
1210 |             handler = K8sHandler(mock_mcp, allow_write=False, allow_sensitive_data_access=True)
1211 | 
1212 |         # Verify that allow_write is set
1213 |         assert handler.allow_write is False
1214 | 
1215 |         # Verify that the tools were registered
1216 |         assert mock_mcp.tool.call_count == 7
1217 | 
1218 |         # Get all call args
1219 |         call_args_list = mock_mcp.tool.call_args_list
1220 | 
1221 |         # Get all tool names that were registered
1222 |         tool_names = [call_args[1]['name'] for call_args in call_args_list]
1223 | 
1224 |         # Verify that all tools are registered
1225 |         assert 'list_k8s_resources' in tool_names
1226 |         assert 'get_pod_logs' in tool_names
1227 |         assert 'get_k8s_events' in tool_names
1228 |         assert 'manage_k8s_resource' in tool_names
1229 |         assert 'apply_yaml' in tool_names
1230 |         assert 'generate_app_manifest' in tool_names
1231 | 
1232 |     @pytest.mark.asyncio
1233 |     async def test_get_pod_logs_success(self, mock_context, mock_mcp, mock_client_cache):
1234 |         """Test get_pod_logs method with successful log retrieval."""
1235 |         # Initialize the K8s handler with sensitive data access enabled
1236 |         with patch(
1237 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1238 |         ):
1239 |             handler = K8sHandler(mock_mcp, allow_sensitive_data_access=True)
1240 | 
1241 |         # Mock get_client
1242 |         mock_k8s_apis = MagicMock()
1243 |         mock_k8s_apis.get_pod_logs.return_value = 'log line 1\nlog line 2\n'
1244 | 
1245 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis) as mock_client:
1246 |             # Get pod logs
1247 |             result = await handler.get_pod_logs(
1248 |                 mock_context,
1249 |                 cluster_name='test-cluster',
1250 |                 namespace='test-namespace',
1251 |                 pod_name='test-pod',
1252 |                 container_name='test-container',
1253 |                 since_seconds=60,
1254 |                 tail_lines=100,
1255 |                 limit_bytes=1024,
1256 |                 previous=True,
1257 |             )
1258 | 
1259 |             # Verify that get_client was called
1260 |             mock_client.assert_called_once_with('test-cluster')
1261 | 
1262 |             # Verify that get_pod_logs was called with the correct parameters
1263 |             mock_k8s_apis.get_pod_logs.assert_called_once_with(
1264 |                 pod_name='test-pod',
1265 |                 namespace='test-namespace',
1266 |                 container_name='test-container',
1267 |                 since_seconds=60,
1268 |                 tail_lines=100,
1269 |                 limit_bytes=1024,
1270 |                 previous=True,
1271 |             )
1272 | 
1273 |             # Verify the result
1274 |             assert not result.isError
1275 |             assert result.pod_name == 'test-pod'
1276 |             assert result.namespace == 'test-namespace'
1277 |             assert result.container_name == 'test-container'
1278 |             assert result.log_lines == ['log line 1', 'log line 2', '']
1279 |             assert isinstance(result.content[0], TextContent)
1280 |             assert (
1281 |                 'Successfully retrieved 3 log lines from pod test-namespace/test-pod (container: test-container)'
1282 |                 in result.content[0].text
1283 |             )
1284 | 
1285 |     @pytest.mark.asyncio
1286 |     async def test_get_pod_logs_minimal(self, mock_context, mock_mcp, mock_client_cache):
1287 |         """Test get_pod_logs method with minimal parameters."""
1288 |         # Initialize the K8s handler with sensitive data access enabled
1289 |         with patch(
1290 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1291 |         ):
1292 |             handler = K8sHandler(mock_mcp, allow_sensitive_data_access=True)
1293 | 
1294 |         # Mock get_client
1295 |         mock_k8s_apis = MagicMock()
1296 |         mock_k8s_apis.get_pod_logs.return_value = 'log line 1\nlog line 2\n'
1297 | 
1298 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis) as mock_client:
1299 |             # Get pod logs with minimal parameters - explicitly pass default values for non-optional parameters
1300 |             result = await handler.get_pod_logs(
1301 |                 mock_context,
1302 |                 cluster_name='test-cluster',
1303 |                 namespace='test-namespace',
1304 |                 pod_name='test-pod',
1305 |                 container_name=None,
1306 |                 since_seconds=None,
1307 |                 tail_lines=100,  # Default value
1308 |                 limit_bytes=10240,  # Default value
1309 |                 previous=False,  # Default value
1310 |             )
1311 | 
1312 |             # Verify that get_client was called
1313 |             mock_client.assert_called_once_with('test-cluster')
1314 | 
1315 |             # Verify that get_pod_logs was called
1316 |             mock_k8s_apis.get_pod_logs.assert_called_once()
1317 | 
1318 |             # Get the call args
1319 |             args, kwargs = mock_k8s_apis.get_pod_logs.call_args
1320 | 
1321 |             # Verify the keyword args
1322 |             assert kwargs['pod_name'] == 'test-pod'
1323 |             assert kwargs['namespace'] == 'test-namespace'
1324 |             assert kwargs['container_name'] is None
1325 | 
1326 |             # Verify the result
1327 |             assert not result.isError
1328 |             assert result.pod_name == 'test-pod'
1329 |             assert result.namespace == 'test-namespace'
1330 |             assert result.container_name is None
1331 |             assert result.log_lines == ['log line 1', 'log line 2', '']
1332 |             assert isinstance(result.content[0], TextContent)
1333 |             assert (
1334 |                 'Successfully retrieved 3 log lines from pod test-namespace/test-pod'
1335 |                 in result.content[0].text
1336 |             )
1337 | 
1338 |     @pytest.mark.asyncio
1339 |     async def test_get_pod_logs_sensitive_data_access_disabled(
1340 |         self, mock_context, mock_mcp, mock_client_cache
1341 |     ):
1342 |         """Test get_pod_logs method with sensitive data access disabled."""
1343 |         # Initialize the K8s handler with sensitive data access disabled
1344 |         with patch(
1345 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1346 |         ):
1347 |             handler = K8sHandler(mock_mcp, allow_sensitive_data_access=False)
1348 | 
1349 |         # Get pod logs with sensitive data access disabled
1350 |         result = await handler.get_pod_logs(
1351 |             mock_context,
1352 |             cluster_name='test-cluster',
1353 |             namespace='test-namespace',
1354 |             pod_name='test-pod',
1355 |             container_name='test-container',
1356 |         )
1357 | 
1358 |         # Verify the result
1359 |         assert result.isError
1360 |         assert result.pod_name == 'test-pod'
1361 |         assert result.namespace == 'test-namespace'
1362 |         assert result.container_name == 'test-container'
1363 |         assert result.log_lines == []
1364 |         assert isinstance(result.content[0], TextContent)
1365 |         assert (
1366 |             'Access to pod logs requires --allow-sensitive-data-access flag'
1367 |             in result.content[0].text
1368 |         )
1369 | 
1370 |     @pytest.mark.asyncio
1371 |     async def test_get_pod_logs_error(self, mock_context, mock_mcp, mock_client_cache):
1372 |         """Test get_pod_logs method with an error."""
1373 |         # Initialize the K8s handler with sensitive data access enabled
1374 |         with patch(
1375 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1376 |         ):
1377 |             handler = K8sHandler(mock_mcp, allow_sensitive_data_access=True)
1378 | 
1379 |         # Mock get_client
1380 |         mock_k8s_apis = MagicMock()
1381 |         mock_k8s_apis.get_pod_logs.side_effect = Exception('Pod not found')
1382 | 
1383 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis) as mock_client:
1384 |             # Get pod logs with an error
1385 |             result = await handler.get_pod_logs(
1386 |                 mock_context,
1387 |                 cluster_name='test-cluster',
1388 |                 namespace='test-namespace',
1389 |                 pod_name='test-pod',
1390 |                 container_name='test-container',
1391 |             )
1392 | 
1393 |             # Verify that get_client was called
1394 |             mock_client.assert_called_once_with('test-cluster')
1395 | 
1396 |             # Verify that get_pod_logs was called
1397 |             mock_k8s_apis.get_pod_logs.assert_called_once()
1398 | 
1399 |             # Get the call args
1400 |             args, kwargs = mock_k8s_apis.get_pod_logs.call_args
1401 | 
1402 |             # Verify the keyword args
1403 |             assert kwargs['pod_name'] == 'test-pod'
1404 |             assert kwargs['namespace'] == 'test-namespace'
1405 |             assert kwargs['container_name'] == 'test-container'
1406 | 
1407 |             # Verify the result
1408 |             assert result.isError
1409 |             assert result.pod_name == 'test-pod'
1410 |             assert result.namespace == 'test-namespace'
1411 |             assert result.container_name == 'test-container'
1412 |             assert result.log_lines == []
1413 |             assert isinstance(result.content[0], TextContent)
1414 |             assert (
1415 |                 'Failed to get logs from pod test-namespace/test-pod (container: test-container): Pod not found'
1416 |                 in result.content[0].text
1417 |             )
1418 | 
1419 |     @pytest.mark.asyncio
1420 |     async def test_get_k8s_events_success(self, mock_context, mock_mcp, mock_client_cache):
1421 |         """Test get_k8s_events method with successful event retrieval."""
1422 |         # Initialize the K8s handler
1423 |         with patch(
1424 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1425 |         ):
1426 |             handler = K8sHandler(mock_mcp, allow_sensitive_data_access=True)
1427 | 
1428 |         # Mock get_client
1429 |         mock_k8s_apis = MagicMock()
1430 |         mock_k8s_apis.get_events.return_value = [
1431 |             {
1432 |                 'first_timestamp': '2023-01-01T00:00:00Z',
1433 |                 'last_timestamp': '2023-01-01T00:05:00Z',
1434 |                 'count': 5,
1435 |                 'message': 'Container created',
1436 |                 'reason': 'Created',
1437 |                 'reporting_component': 'kubelet',
1438 |                 'type': 'Normal',
1439 |             },
1440 |             {
1441 |                 'first_timestamp': '2023-01-01T00:05:00Z',
1442 |                 'last_timestamp': '2023-01-01T00:10:00Z',
1443 |                 'count': 1,
1444 |                 'message': 'Container started',
1445 |                 'reason': 'Started',
1446 |                 'reporting_component': 'kubelet',
1447 |                 'type': 'Normal',
1448 |             },
1449 |         ]
1450 | 
1451 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis) as mock_client:
1452 |             # Get events
1453 |             result = await handler.get_k8s_events(
1454 |                 mock_context,
1455 |                 cluster_name='test-cluster',
1456 |                 kind='Pod',
1457 |                 name='test-pod',
1458 |                 namespace='test-namespace',
1459 |             )
1460 | 
1461 |             # Verify that get_client was called
1462 |             mock_client.assert_called_once_with('test-cluster')
1463 | 
1464 |             # Verify that get_events was called with the correct parameters
1465 |             mock_k8s_apis.get_events.assert_called_once_with(
1466 |                 kind='Pod',
1467 |                 name='test-pod',
1468 |                 namespace='test-namespace',
1469 |             )
1470 | 
1471 |             # Verify the result
1472 |             assert not result.isError
1473 |             assert result.involved_object_kind == 'Pod'
1474 |             assert result.involved_object_name == 'test-pod'
1475 |             assert result.involved_object_namespace == 'test-namespace'
1476 |             assert result.count == 2
1477 |             assert len(result.events) == 2
1478 | 
1479 |             # Check first event
1480 |             assert result.events[0].first_timestamp == '2023-01-01T00:00:00Z'
1481 |             assert result.events[0].last_timestamp == '2023-01-01T00:05:00Z'
1482 |             assert result.events[0].count == 5
1483 |             assert result.events[0].message == 'Container created'
1484 |             assert result.events[0].reason == 'Created'
1485 |             assert result.events[0].reporting_component == 'kubelet'
1486 |             assert result.events[0].type == 'Normal'
1487 | 
1488 |             # Check second event
1489 |             assert result.events[1].message == 'Container started'
1490 | 
1491 |             # Check content
1492 |             assert isinstance(result.content[0], TextContent)
1493 |             assert (
1494 |                 'Successfully retrieved 2 events for Pod test-namespace/test-pod'
1495 |                 in result.content[0].text
1496 |             )
1497 | 
1498 |     @pytest.mark.asyncio
1499 |     async def test_get_k8s_events_empty(self, mock_context, mock_mcp, mock_client_cache):
1500 |         """Test get_k8s_events method with no events found."""
1501 |         # Initialize the K8s handler
1502 |         with patch(
1503 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1504 |         ):
1505 |             handler = K8sHandler(mock_mcp, allow_sensitive_data_access=True)
1506 | 
1507 |         # Mock get_client
1508 |         mock_k8s_apis = MagicMock()
1509 |         mock_k8s_apis.get_events.return_value = []
1510 | 
1511 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis) as mock_client:
1512 |             # Get events
1513 |             result = await handler.get_k8s_events(
1514 |                 mock_context,
1515 |                 cluster_name='test-cluster',
1516 |                 kind='Pod',
1517 |                 name='test-pod',
1518 |                 namespace='test-namespace',
1519 |             )
1520 | 
1521 |             # Verify that get_client was called
1522 |             mock_client.assert_called_once_with('test-cluster')
1523 | 
1524 |             # Verify that get_events was called
1525 |             mock_k8s_apis.get_events.assert_called_once()
1526 | 
1527 |             # Verify the result
1528 |             assert not result.isError
1529 |             assert result.involved_object_kind == 'Pod'
1530 |             assert result.involved_object_name == 'test-pod'
1531 |             assert result.involved_object_namespace == 'test-namespace'
1532 |             assert result.count == 0
1533 |             assert len(result.events) == 0
1534 |             assert isinstance(result.content[0], TextContent)
1535 |             assert (
1536 |                 'Successfully retrieved 0 events for Pod test-namespace/test-pod'
1537 |                 in result.content[0].text
1538 |             )
1539 | 
1540 |     @pytest.mark.asyncio
1541 |     async def test_get_k8s_events_sensitive_data_access_disabled(
1542 |         self, mock_context, mock_mcp, mock_client_cache
1543 |     ):
1544 |         """Test get_k8s_events method with sensitive data access disabled."""
1545 |         # Initialize the K8s handler with sensitive data access disabled
1546 |         with patch(
1547 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1548 |         ):
1549 |             handler = K8sHandler(mock_mcp, allow_sensitive_data_access=False)
1550 | 
1551 |         # Get events with sensitive data access disabled
1552 |         result = await handler.get_k8s_events(
1553 |             mock_context,
1554 |             cluster_name='test-cluster',
1555 |             kind='Pod',
1556 |             name='test-pod',
1557 |             namespace='test-namespace',
1558 |         )
1559 | 
1560 |         # Verify the result
1561 |         assert result.isError
1562 |         assert result.involved_object_kind == 'Pod'
1563 |         assert result.involved_object_name == 'test-pod'
1564 |         assert result.involved_object_namespace == 'test-namespace'
1565 |         assert result.count == 0
1566 |         assert len(result.events) == 0
1567 |         assert isinstance(result.content[0], TextContent)
1568 |         assert (
1569 |             'Access to Kubernetes events requires --allow-sensitive-data-access flag'
1570 |             in result.content[0].text
1571 |         )
1572 | 
1573 |     @pytest.mark.asyncio
1574 |     async def test_get_k8s_events_error(self, mock_context, mock_mcp, mock_client_cache):
1575 |         """Test get_k8s_events method with an error."""
1576 |         # Initialize the K8s handler with sensitive data access enabled
1577 |         with patch(
1578 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1579 |         ):
1580 |             handler = K8sHandler(mock_mcp, allow_sensitive_data_access=True)
1581 | 
1582 |         # Mock get_client
1583 |         mock_k8s_apis = MagicMock()
1584 |         mock_k8s_apis.get_events.side_effect = Exception('Failed to get events')
1585 | 
1586 |         with patch.object(handler, 'get_client', return_value=mock_k8s_apis) as mock_client:
1587 |             # Get events with an error
1588 |             result = await handler.get_k8s_events(
1589 |                 mock_context,
1590 |                 cluster_name='test-cluster',
1591 |                 kind='Pod',
1592 |                 name='test-pod',
1593 |                 namespace='test-namespace',
1594 |             )
1595 | 
1596 |             # Verify that get_client was called
1597 |             mock_client.assert_called_once_with('test-cluster')
1598 | 
1599 |             # Verify that get_events was called
1600 |             mock_k8s_apis.get_events.assert_called_once()
1601 | 
1602 |             # Verify the result
1603 |             assert result.isError
1604 |             assert result.involved_object_kind == 'Pod'
1605 |             assert result.involved_object_name == 'test-pod'
1606 |             assert result.involved_object_namespace == 'test-namespace'
1607 |             assert result.count == 0
1608 |             assert len(result.events) == 0
1609 |             assert isinstance(result.content[0], TextContent)
1610 |             assert (
1611 |                 'Failed to get events for Pod test-namespace/test-pod: Failed to get events'
1612 |                 in result.content[0].text
1613 |             )
1614 | 
1615 |     def test_remove_managed_fields(self, mock_mcp, mock_client_cache):
1616 |         """Test remove_managed_fields method for removing managed_fields from Kubernetes resources."""
1617 |         # Initialize the K8s handler
1618 |         with patch(
1619 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1620 |         ):
1621 |             handler = K8sHandler(mock_mcp)
1622 | 
1623 |         # Create a deep copy of the input to avoid modifying the original
1624 |         import copy
1625 | 
1626 |         # Test case 1: Resource with managedFields (camelCase as used by dynamic client)
1627 |         resource_with_managed_fields = {
1628 |             'metadata': {
1629 |                 'name': 'test-pod',
1630 |                 'namespace': 'default',
1631 |                 'managedFields': [
1632 |                     {
1633 |                         'manager': 'kubectl',
1634 |                         'operation': 'Update',
1635 |                         'apiVersion': 'v1',
1636 |                         'time': '2023-01-01T00:00:00Z',
1637 |                         'fieldsType': 'FieldsV1',
1638 |                         'fieldsV1': {'f:metadata': {'f:labels': {'.': {}, 'f:app': {}}}},
1639 |                     }
1640 |                 ],
1641 |             },
1642 |             'spec': {'containers': [{'name': 'container1', 'image': 'nginx'}]},
1643 |         }
1644 | 
1645 |         expected_result = {
1646 |             'metadata': {'name': 'test-pod', 'namespace': 'default'},
1647 |             'spec': {'containers': [{'name': 'container1', 'image': 'nginx'}]},
1648 |         }
1649 | 
1650 |         # Make a deep copy to avoid modifying the original
1651 |         input_copy = copy.deepcopy(resource_with_managed_fields)
1652 |         result = handler.remove_managed_fields(input_copy)
1653 |         assert result == expected_result
1654 | 
1655 |         # Test case 2: Resource without managedFields
1656 |         resource_without_managed_fields = {
1657 |             'metadata': {'name': 'test-pod', 'namespace': 'default'},
1658 |             'spec': {'containers': [{'name': 'container1', 'image': 'nginx'}]},
1659 |         }
1660 | 
1661 |         # The result should be the same as the input
1662 |         result = handler.remove_managed_fields(resource_without_managed_fields)
1663 |         assert result == resource_without_managed_fields
1664 | 
1665 |         # Test case 3: Resource without metadata
1666 |         resource_without_metadata = {
1667 |             'kind': 'Pod',
1668 |             'apiVersion': 'v1',
1669 |             'spec': {'containers': [{'name': 'container1', 'image': 'nginx'}]},
1670 |         }
1671 | 
1672 |         # The result should be the same as the input
1673 |         result = handler.remove_managed_fields(resource_without_metadata)
1674 |         assert result == resource_without_metadata
1675 | 
1676 |         # Test case 4: Non-dict input
1677 |         non_dict_input = {}  # Use empty dict instead of string to avoid type error
1678 |         result = handler.remove_managed_fields(non_dict_input)
1679 |         assert result == non_dict_input
1680 | 
1681 |     def test_cleanup_resource_response(self, mock_mcp, mock_client_cache):
1682 |         """Test cleanup_resource_response method for removing managed fields and null values."""
1683 |         # Initialize the K8s handler
1684 |         with patch(
1685 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1686 |         ):
1687 |             handler = K8sHandler(mock_mcp)
1688 | 
1689 |         # Create a complex resource with both managed_fields and null values
1690 |         complex_resource = {
1691 |             'kind': 'Pod',
1692 |             'apiVersion': 'v1',
1693 |             'metadata': {
1694 |                 'name': 'test-pod',
1695 |                 'namespace': 'default',
1696 |                 'managedFields': [
1697 |                     {
1698 |                         'manager': 'kubectl',
1699 |                         'operation': 'Update',
1700 |                         'apiVersion': 'v1',
1701 |                         'time': '2023-01-01T00:00:00Z',
1702 |                         'fieldsType': 'FieldsV1',
1703 |                         'fieldsV1': {'f:metadata': {'f:labels': {'.': {}, 'f:app': {}}}},
1704 |                     }
1705 |                 ],
1706 |                 'labels': {'app': 'test', 'environment': None},
1707 |                 'annotations': None,
1708 |             },
1709 |             'spec': {
1710 |                 'containers': [
1711 |                     {'name': 'container1', 'image': 'nginx', 'resources': None},
1712 |                     None,
1713 |                     {
1714 |                         'name': 'container2',
1715 |                         'image': 'redis',
1716 |                         'ports': [{'containerPort': 6379}, {'containerPort': None}],
1717 |                     },
1718 |                 ],
1719 |                 'volumes': None,
1720 |             },
1721 |             'status': None,
1722 |         }
1723 | 
1724 |         # Expected result after cleanup
1725 |         expected_result = {
1726 |             'kind': 'Pod',
1727 |             'apiVersion': 'v1',
1728 |             'metadata': {'name': 'test-pod', 'namespace': 'default', 'labels': {'app': 'test'}},
1729 |             'spec': {
1730 |                 'containers': [
1731 |                     {'name': 'container1', 'image': 'nginx'},
1732 |                     {
1733 |                         'name': 'container2',
1734 |                         'image': 'redis',
1735 |                         'ports': [{'containerPort': 6379}, {}],
1736 |                     },
1737 |                 ]
1738 |             },
1739 |         }
1740 | 
1741 |         # Test with spies to verify both methods are called
1742 |         with patch.object(
1743 |             handler, 'remove_managed_fields', wraps=handler.remove_managed_fields
1744 |         ) as mock_remove:
1745 |             with patch.object(
1746 |                 handler, 'filter_null_values', wraps=handler.filter_null_values
1747 |             ) as mock_filter:
1748 |                 result = handler.cleanup_resource_response(complex_resource)
1749 | 
1750 |                 # Verify that both methods were called
1751 |                 mock_remove.assert_called_once_with(complex_resource)
1752 |                 # We don't check the exact number of calls for filter_null_values since it's recursive
1753 |                 # and will be called for each nested element
1754 |                 assert mock_filter.called
1755 | 
1756 |                 # Just verify that filter_null_values was called at least once
1757 |                 # We can't easily check the exact argument since remove_managed_fields modifies the input
1758 | 
1759 |                 # Verify the final result
1760 |                 assert result == expected_result
1761 | 
1762 |         # Test with a simple string input
1763 |         simple_input = 'simple string'
1764 |         result = handler.cleanup_resource_response(simple_input)
1765 |         assert result == simple_input
1766 | 
1767 |     def test_remove_checkov_skip_annotations(self, mock_mcp, mock_client_cache):
1768 |         """Test _remove_checkov_skip_annotations method directly to ensure line 807 is covered."""
1769 |         # Initialize the K8s handler
1770 |         with patch(
1771 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1772 |         ):
1773 |             handler = K8sHandler(mock_mcp)
1774 | 
1775 |         # Test case 1: YAML with only checkov skip annotations (should remove annotations completely)
1776 |         yaml_content = """apiVersion: apps/v1
1777 | kind: Deployment
1778 | metadata:
1779 |   name: test-app
1780 |   namespace: default
1781 |   annotations:
1782 |     checkov.io/skip1: "CKV_K8S_14=We're using a specific image version"
1783 |     checkov.io/skip2: "CKV_K8S_43=Resource limits are set appropriately"
1784 | spec:
1785 |   replicas: 3"""
1786 | 
1787 |         expected_result = """apiVersion: apps/v1
1788 | kind: Deployment
1789 | metadata:
1790 |   name: test-app
1791 |   namespace: default
1792 | spec:
1793 |   replicas: 3
1794 | """
1795 | 
1796 |         result = handler._remove_checkov_skip_annotations(yaml_content)
1797 |         # Normalize whitespace for comparison
1798 |         result = result.replace(' ', '').replace('\n', '')
1799 |         expected_result = expected_result.replace(' ', '').replace('\n', '')
1800 |         assert result == expected_result
1801 | 
1802 |         # Test case 2: YAML with mixed annotations (should keep non-checkov annotations)
1803 |         yaml_content = """apiVersion: apps/v1
1804 | kind: Deployment
1805 | metadata:
1806 |   name: test-app
1807 |   namespace: default
1808 |   annotations:
1809 |     checkov.io/skip1: "CKV_K8S_14=We're using a specific image version"
1810 |     other-annotation: "This should be preserved"
1811 | spec:
1812 |   replicas: 3"""
1813 | 
1814 |         expected_result = """apiVersion: apps/v1
1815 | kind: Deployment
1816 | metadata:
1817 |   name: test-app
1818 |   namespace: default
1819 |   annotations:
1820 |     other-annotation: This should be preserved
1821 | spec:
1822 |   replicas: 3
1823 | """
1824 | 
1825 |         result = handler._remove_checkov_skip_annotations(yaml_content)
1826 |         assert 'other-annotation: This should be preserved' in result
1827 | 
1828 |     def test_filter_null_values(self, mock_mcp, mock_client_cache):
1829 |         """Test filter_null_values method for removing null values from data structures."""
1830 |         # Initialize the K8s handler
1831 |         with patch(
1832 |             'awslabs.eks_mcp_server.k8s_handler.K8sClientCache', return_value=mock_client_cache
1833 |         ):
1834 |             handler = K8sHandler(mock_mcp)
1835 | 
1836 |         # Test case 1: Simple dictionary with null values
1837 |         input_dict = {'key1': 'value1', 'key2': None, 'key3': 'value3', 'key4': None}
1838 |         expected_dict = {'key1': 'value1', 'key3': 'value3'}
1839 |         result = handler.filter_null_values(input_dict)
1840 |         assert result == expected_dict
1841 | 
1842 |         # Test case 2: Nested dictionary with null values
1843 |         input_nested_dict = {
1844 |             'key1': 'value1',
1845 |             'key2': None,
1846 |             'key3': {
1847 |                 'nested1': 'nested_value1',
1848 |                 'nested2': None,
1849 |                 'nested3': {'deep1': 'deep_value1', 'deep2': None},
1850 |             },
1851 |         }
1852 |         expected_nested_dict = {
1853 |             'key1': 'value1',
1854 |             'key3': {'nested1': 'nested_value1', 'nested3': {'deep1': 'deep_value1'}},
1855 |         }
1856 |         result = handler.filter_null_values(input_nested_dict)
1857 |         assert result == expected_nested_dict
1858 | 
1859 |         # Test case 3: List with null values
1860 |         input_list = ['item1', None, 'item2', None, 'item3']
1861 |         expected_list = ['item1', 'item2', 'item3']
1862 |         result = handler.filter_null_values(input_list)
1863 |         assert result == expected_list
1864 | 
1865 |         # Test case 4: List of dictionaries with null values
1866 |         input_list_of_dicts = [
1867 |             {'key1': 'value1', 'key2': None},
1868 |             None,
1869 |             {'key3': None, 'key4': 'value4'},
1870 |         ]
1871 |         expected_list_of_dicts = [{'key1': 'value1'}, {'key4': 'value4'}]
1872 |         result = handler.filter_null_values(input_list_of_dicts)
1873 |         assert result == expected_list_of_dicts
1874 | 
1875 |         # Test case 5: Primitive values (non-dict, non-list)
1876 |         assert handler.filter_null_values('string') == 'string'
1877 |         assert handler.filter_null_values(123) == 123
1878 |         assert handler.filter_null_values(True)
1879 |         assert handler.filter_null_values(None) is None  # None input should return None
1880 | 
1881 |         # Test case 6: Empty containers
1882 |         assert handler.filter_null_values({}) == {}
1883 |         assert handler.filter_null_values([]) == []
1884 | 
1885 |         # Test case 7: Complex nested structure
1886 |         complex_input = {
1887 |             'metadata': {
1888 |                 'name': 'test-pod',
1889 |                 'namespace': 'default',
1890 |                 'labels': {'app': 'test', 'environment': None},
1891 |                 'annotations': None,
1892 |             },
1893 |             'spec': {
1894 |                 'containers': [
1895 |                     {'name': 'container1', 'image': 'nginx', 'resources': None},
1896 |                     None,
1897 |                     {
1898 |                         'name': 'container2',
1899 |                         'image': 'redis',
1900 |                         'ports': [{'containerPort': 6379}, {'containerPort': None}],
1901 |                     },
1902 |                 ],
1903 |                 'volumes': None,
1904 |             },
1905 |             'status': None,
1906 |         }
1907 | 
1908 |         expected_complex = {
1909 |             'metadata': {'name': 'test-pod', 'namespace': 'default', 'labels': {'app': 'test'}},
1910 |             'spec': {
1911 |                 'containers': [
1912 |                     {'name': 'container1', 'image': 'nginx'},
1913 |                     {
1914 |                         'name': 'container2',
1915 |                         'image': 'redis',
1916 |                         'ports': [{'containerPort': 6379}, {}],
1917 |                     },
1918 |                 ]
1919 |             },
1920 |         }
1921 | 
1922 |         result = handler.filter_null_values(complex_input)
1923 |         assert result == expected_complex
1924 | 
```
Page 544/553FirstPrevNextLast