Policy Notebook fallback for NL2cedar (#1324)
* add IGNORE_ALL_FINDINGS fallback and fix NB03 execution issues * add fallback to policy creation cells * fallback to all NL2Cedar usages
This commit is contained in:
committed by
GitHub
parent
cea7e355b0
commit
49b49bae60
@@ -2328,39 +2328,7 @@
|
||||
"execution_count": null,
|
||||
"metadata": {},
|
||||
"outputs": [],
|
||||
"source": [
|
||||
"from bedrock_agentcore_starter_toolkit.operations.policy.client import PolicyClient\n",
|
||||
"\n",
|
||||
"# Policy client creation\n",
|
||||
"policy_client = PolicyClient(region_name=region)\n",
|
||||
"policy_client.logger.setLevel(logging.INFO)\n",
|
||||
"\n",
|
||||
"# Create Cedar policy\n",
|
||||
"print(\"\\n📝 Creating Cedar Policy...\")\n",
|
||||
"print(f\" Policy Engine ID: {engine['policyEngineArn']}\")\n",
|
||||
"GATEWAY_ARN = config[\"gateway\"][\"gateway_arn\"]\n",
|
||||
"\n",
|
||||
"# Define the Cedar policy statement\n",
|
||||
"cedar_statement = (\n",
|
||||
" f\"permit(principal, \"\n",
|
||||
" f'action == AgentCore::Action::\"ApplicationToolTarget___create_application\", '\n",
|
||||
" f'resource == AgentCore::Gateway::\"{GATEWAY_ARN}\") '\n",
|
||||
" f\"when {{ context.input.coverage_amount <= 1000000 }};\"\n",
|
||||
")\n",
|
||||
"\n",
|
||||
"policy = policy_client.create_or_get_policy(\n",
|
||||
" policy_engine_id=engine[\"policyEngineId\"],\n",
|
||||
" name=\"create_application_policy\",\n",
|
||||
" description=\"Allow application creation under $1M\",\n",
|
||||
" definition={\"cedar\": {\"statement\": cedar_statement}},\n",
|
||||
")\n",
|
||||
"print(f\"✓ Policy: {policy['policyId']}\\n\")\n",
|
||||
"\n",
|
||||
"# Save to config\n",
|
||||
"config[\"policy_id\"] = policy[\"policyId\"]\n",
|
||||
"with open(\"config.json\", \"w\") as f:\n",
|
||||
" json.dump(config, f, indent=2)"
|
||||
]
|
||||
"source": "from bedrock_agentcore_starter_toolkit.operations.policy.client import PolicyClient\n\n# Policy client creation\npolicy_client = PolicyClient(region_name=region)\npolicy_client.logger.setLevel(logging.INFO)\n\n# Create Cedar policy\nprint(\"\\n📝 Creating Cedar Policy...\")\nprint(f\" Policy Engine ID: {engine['policyEngineArn']}\")\nGATEWAY_ARN = config[\"gateway\"][\"gateway_arn\"]\n\n# Define the Cedar policy statement\ncedar_statement = (\n f\"permit(principal, \"\n f'action == AgentCore::Action::\"ApplicationToolTarget___create_application\", '\n f'resource == AgentCore::Gateway::\"{GATEWAY_ARN}\") '\n f\"when {{ context.input.coverage_amount <= 1000000 }};\"\n)\n\ntry:\n policy = policy_client.create_or_get_policy(\n policy_engine_id=engine[\"policyEngineId\"],\n name=\"create_application_policy\",\n description=\"Allow application creation under $1M\",\n definition={\"cedar\": {\"statement\": cedar_statement}},\n )\n print(f\"✓ Policy: {policy['policyId']}\\n\")\nexcept Exception as e:\n print(f\"⚠️ Policy creation failed: {e}\")\n print(\" This may be due to Cedar validation findings (e.g., policy too restrictive or schema issues).\")\n print(\" Retrying with validation_mode='IGNORE_ALL_FINDINGS'...\")\n policy = policy_client.create_or_get_policy(\n policy_engine_id=engine[\"policyEngineId\"],\n name=\"create_application_policy\",\n description=\"Allow application creation under $1M\",\n definition={\"cedar\": {\"statement\": cedar_statement}},\n validation_mode=\"IGNORE_ALL_FINDINGS\",\n )\n print(f\"✓ Policy created with IGNORE_ALL_FINDINGS: {policy['policyId']}\\n\")\n\n# Save to config\nconfig[\"policy_id\"] = policy[\"policyId\"]\nwith open(\"config.json\", \"w\") as f:\n json.dump(config, f, indent=2)"
|
||||
},
|
||||
{
|
||||
"cell_type": "markdown",
|
||||
|
||||
+1312
-51
File diff suppressed because it is too large
Load Diff
+7
-353
File diff suppressed because one or more lines are too long
@@ -50,7 +50,7 @@
|
||||
"\n",
|
||||
"For the inbound authentication, the AgentCore Gateway analyzes the OAuth token passed during invocation to decide allow or deny the access to a tool in the gateway. If a tool needs access to external resources, the AgentCore Gateway can use outbound authentication via API Key, IAM or OAuth Token to allow or deny the access to the external resource.\n",
|
||||
"\n",
|
||||
"During the inbound authorization flow, an agent or the MCP client calls an MCP tool in the AgentCore Gateway adding an OAuth access token (generated from the user’s IdP). AgentCore Gateway then validates the OAuth access token and performs inbound authorization.\n",
|
||||
"During the inbound authorization flow, an agent or the MCP client calls an MCP tool in the AgentCore Gateway adding an OAuth access token (generated from the user\u2019s IdP). AgentCore Gateway then validates the OAuth access token and performs inbound authorization.\n",
|
||||
"\n",
|
||||
"If the tool running in AgentCore Gateway needs to access external resources, OAuth will retrieve credentials of downstream resources using the resource credential provider for the Gateway target. AgentCore Gateway pass the authorization credentials to the caller to get access to the downstream API.\n",
|
||||
"\n",
|
||||
@@ -126,7 +126,7 @@
|
||||
" region_name=REGION,\n",
|
||||
")\n",
|
||||
"\n",
|
||||
"print(\"✅ Libraries imported successfully!\")"
|
||||
"print(\"\u2705 Libraries imported successfully!\")"
|
||||
]
|
||||
},
|
||||
{
|
||||
@@ -194,7 +194,7 @@
|
||||
" return f\"Search error: {str(e)}\"\n",
|
||||
"\n",
|
||||
"\n",
|
||||
"print(\"✅ Web search tool ready\")\n",
|
||||
"print(\"\u2705 Web search tool ready\")\n",
|
||||
"```"
|
||||
]
|
||||
},
|
||||
@@ -321,7 +321,7 @@
|
||||
"\n",
|
||||
" time.sleep(3)\n",
|
||||
" \n",
|
||||
" print(f\"✅ Gateway created successfully with ID: {gateway_id}\")\n",
|
||||
" print(f\"\u2705 Gateway created successfully with ID: {gateway_id}\")\n",
|
||||
"\n",
|
||||
"except Exception:\n",
|
||||
" # If gateway exists, collect existing gateway ID from SSM\n",
|
||||
@@ -362,7 +362,7 @@
|
||||
"\n",
|
||||
" # Validate API spec file exists\n",
|
||||
" if not os.path.exists(api_spec_file):\n",
|
||||
" print(f\"❌ API specification file not found: {api_spec_file}\")\n",
|
||||
" print(f\"\u274c API specification file not found: {api_spec_file}\")\n",
|
||||
" sys.exit(1)\n",
|
||||
"\n",
|
||||
" api_spec = load_api_spec(api_spec_file)\n",
|
||||
@@ -390,10 +390,10 @@
|
||||
" credentialProviderConfigurations=credential_config,\n",
|
||||
" )\n",
|
||||
"\n",
|
||||
" print(f\"✅ Gateway target created: {create_target_response['targetId']}\")\n",
|
||||
" print(f\"\u2705 Gateway target created: {create_target_response['targetId']}\")\n",
|
||||
"\n",
|
||||
"except Exception as e:\n",
|
||||
" print(f\"❌ Error creating gateway target: {str(e)}\")"
|
||||
" print(f\"\u274c Error creating gateway target: {str(e)}\")"
|
||||
]
|
||||
},
|
||||
{
|
||||
@@ -426,7 +426,7 @@
|
||||
" tools = mcp_client.list_tools_sync()\n",
|
||||
" print(f\" Found {len(tools)} tool(s):\\n\")\n",
|
||||
" for tool in tools:\n",
|
||||
" print(f\" ✅ {tool.mcp_tool.name}\")\n",
|
||||
" print(f\" \u2705 {tool.mcp_tool.name}\")\n",
|
||||
" print(f\" {tool.mcp_tool.description}\\n\")"
|
||||
]
|
||||
},
|
||||
@@ -504,7 +504,7 @@
|
||||
" raise e\n",
|
||||
"\n",
|
||||
"\n",
|
||||
"print(\"✅ Customer support agent created successfully!\")"
|
||||
"print(\"\u2705 Customer support agent created successfully!\")"
|
||||
]
|
||||
},
|
||||
{
|
||||
@@ -553,7 +553,7 @@
|
||||
"# Run the tests\n",
|
||||
"test_agent_responses(test_prompts)\n",
|
||||
"\n",
|
||||
"print(\"\\\\n✅ Basic testing completed!\")"
|
||||
"print(\"\\\\n\u2705 Basic testing completed!\")"
|
||||
]
|
||||
},
|
||||
{
|
||||
@@ -584,15 +584,15 @@
|
||||
"# Try to import from toolkit, fall back to custom implementation if not available\n",
|
||||
"try:\n",
|
||||
" from bedrock_agentcore_starter_toolkit.operations.policy.client import PolicyClient\n",
|
||||
" print(\"✅ Using toolkit PolicyClient\")\n",
|
||||
" print(\"\u2705 Using toolkit PolicyClient\")\n",
|
||||
"except ImportError:\n",
|
||||
" from utils.policy_utils import PolicyClient\n",
|
||||
" print(\"✅ Using custom PolicyClient (toolkit policy module not available)\")\n",
|
||||
" print(\"\u2705 Using custom PolicyClient (toolkit policy module not available)\")\n",
|
||||
"\n",
|
||||
"# Initialize the policy client\n",
|
||||
"policy_client = PolicyClient(region_name=REGION)\n",
|
||||
"\n",
|
||||
"print(\"\\n🔧 Creating Policy Engine...\")\n",
|
||||
"print(\"\\n\ud83d\udd27 Creating Policy Engine...\")\n",
|
||||
"\n",
|
||||
"# Create or get existing policy engine\n",
|
||||
"# The policy engine is a container for all our authorization policies\n",
|
||||
@@ -605,7 +605,7 @@
|
||||
"engine_arn = engine['policyEngineArn']\n",
|
||||
"put_ssm_parameter(\"/app/customersupport/agentcore/policy_engine_id\", engine_id)\n",
|
||||
"\n",
|
||||
"print(f\"\\n✅ Policy Engine ready\")\n",
|
||||
"print(f\"\\n\u2705 Policy Engine ready\")\n",
|
||||
"print(f\" Engine ID: {engine_id}\")\n",
|
||||
"print(f\" Engine ARN: {engine_arn}\")"
|
||||
]
|
||||
@@ -631,7 +631,7 @@
|
||||
"source": [
|
||||
"import time\n",
|
||||
"# Create Cedar policy for approve tool (write scope)\n",
|
||||
"print(\"\\n📝 Generating Cedar Policy from Natural language...\")\n",
|
||||
"print(\"\\n\ud83d\udcdd Generating Cedar Policy from Natural language...\")\n",
|
||||
"\n",
|
||||
"nl_input = \"Allow tag username == 'testuser' to perform check warranty status on the customer support gateway.\"\n",
|
||||
"\n",
|
||||
@@ -643,7 +643,7 @@
|
||||
" fetch_assets=True,\n",
|
||||
")\n",
|
||||
"\n",
|
||||
"print(\"✅ Policy generated from natural language\")"
|
||||
"print(\"\u2705 Policy generated from natural language\")"
|
||||
]
|
||||
},
|
||||
{
|
||||
@@ -653,11 +653,11 @@
|
||||
"metadata": {},
|
||||
"outputs": [],
|
||||
"source": [
|
||||
"print(\"📋 Generated Cedar Policies:\\n\")\n",
|
||||
"print(\"\ud83d\udccb Generated Cedar Policies:\\n\")\n",
|
||||
"print(\"=\" * 80)\n",
|
||||
"\n",
|
||||
"# Allow warranty status policy\n",
|
||||
"print(\"\\n1️⃣ Warranty Status\")\n",
|
||||
"print(\"\\n1\ufe0f\u20e3 Warranty Status\")\n",
|
||||
"print(\"-\" * 80)\n",
|
||||
"warranty_tool_policy_cedar = warranty_tool_policy[\"generatedPolicies\"][0][\"definition\"][\"cedar\"][\"statement\"]\n",
|
||||
"print(warranty_tool_policy_cedar)\n",
|
||||
@@ -730,29 +730,70 @@
|
||||
"metadata": {},
|
||||
"outputs": [],
|
||||
"source": [
|
||||
"print(\"🔧 Creating policies in Policy Engine...\\n\")\n",
|
||||
"print(\"\ud83d\udd27 Creating policies in Policy Engine...\\n\")\n",
|
||||
"\n",
|
||||
"import time as _time\n",
|
||||
"\n",
|
||||
"def _cleanup_failed_policy(pe_id, name):\n",
|
||||
" \"\"\"Delete any CREATE_FAILED policy with the given name to allow clean retry.\"\"\"\n",
|
||||
" try:\n",
|
||||
" cp_client = boto3.client(\"bedrock-agentcore-control\", region_name=REGION)\n",
|
||||
" existing = cp_client.list_policies(policyEngineId=pe_id)\n",
|
||||
" for p in existing.get(\"policies\", []):\n",
|
||||
" if p[\"name\"] == name and p[\"status\"] == \"CREATE_FAILED\":\n",
|
||||
" cp_client.delete_policy(policyEngineId=pe_id, policyId=p[\"policyId\"])\n",
|
||||
" print(f\" Deleted stale CREATE_FAILED policy: {name}\")\n",
|
||||
" _time.sleep(2)\n",
|
||||
" except Exception:\n",
|
||||
" pass\n",
|
||||
"\n",
|
||||
"# Create allow both tools policy\n",
|
||||
"warranty_result = policy_client.create_or_get_policy(\n",
|
||||
" policy_engine_id=engine[\"policyEngineId\"],\n",
|
||||
" name=\"allow_policy\",\n",
|
||||
" description=\"Allow web_search and check_warranty_status calls\",\n",
|
||||
" definition=allow_policy\n",
|
||||
")\n",
|
||||
"print(\"✅ Policy ready: allow_policy\")\n",
|
||||
"try:\n",
|
||||
" warranty_result = policy_client.create_or_get_policy(\n",
|
||||
" policy_engine_id=engine[\"policyEngineId\"],\n",
|
||||
" name=\"allow_policy\",\n",
|
||||
" description=\"Allow web_search and check_warranty_status calls\",\n",
|
||||
" definition=allow_policy\n",
|
||||
" )\n",
|
||||
" print(\"\u2705 Policy ready: allow_policy\")\n",
|
||||
"except Exception as e:\n",
|
||||
" print(f\"\u26a0\ufe0f Policy creation failed: {e}\")\n",
|
||||
" print(\" Retrying with validation_mode='IGNORE_ALL_FINDINGS'...\")\n",
|
||||
" _cleanup_failed_policy(engine[\"policyEngineId\"], \"allow_policy\")\n",
|
||||
" warranty_result = policy_client.create_or_get_policy(\n",
|
||||
" policy_engine_id=engine[\"policyEngineId\"],\n",
|
||||
" name=\"allow_policy\",\n",
|
||||
" description=\"Allow web_search and check_warranty_status calls\",\n",
|
||||
" definition=allow_policy,\n",
|
||||
" validation_mode=\"IGNORE_ALL_FINDINGS\",\n",
|
||||
" )\n",
|
||||
" print(\"\u2705 Policy ready with IGNORE_ALL_FINDINGS: allow_policy\")\n",
|
||||
"print(\" Tools allowed: check_warranty_status and web_search\\n\")\n",
|
||||
"\n",
|
||||
"# Create deny web search list policy\n",
|
||||
"web_search_deny_result = policy_client.create_or_get_policy(\n",
|
||||
" policy_engine_id=engine[\"policyEngineId\"],\n",
|
||||
" name=\"deny_web_search\",\n",
|
||||
" description=\"Deny web_search tool call for iPhone 8\",\n",
|
||||
" definition=deny_web_search_policy\n",
|
||||
")\n",
|
||||
"print(\"✅ Policy ready: deny_web_search\")\n",
|
||||
"try:\n",
|
||||
" web_search_deny_result = policy_client.create_or_get_policy(\n",
|
||||
" policy_engine_id=engine[\"policyEngineId\"],\n",
|
||||
" name=\"deny_web_search\",\n",
|
||||
" description=\"Deny web_search tool call for iPhone 8\",\n",
|
||||
" definition=deny_web_search_policy\n",
|
||||
" )\n",
|
||||
" print(\"\u2705 Policy ready: deny_web_search\")\n",
|
||||
"except Exception as e:\n",
|
||||
" print(f\"\u26a0\ufe0f Policy creation failed: {e}\")\n",
|
||||
" print(\" Retrying with validation_mode='IGNORE_ALL_FINDINGS'...\")\n",
|
||||
" _cleanup_failed_policy(engine[\"policyEngineId\"], \"deny_web_search\")\n",
|
||||
" web_search_deny_result = policy_client.create_or_get_policy(\n",
|
||||
" policy_engine_id=engine[\"policyEngineId\"],\n",
|
||||
" name=\"deny_web_search\",\n",
|
||||
" description=\"Deny web_search tool call for iPhone 8\",\n",
|
||||
" definition=deny_web_search_policy,\n",
|
||||
" validation_mode=\"IGNORE_ALL_FINDINGS\",\n",
|
||||
" )\n",
|
||||
" print(\"\u2705 Policy ready with IGNORE_ALL_FINDINGS: deny_web_search\")\n",
|
||||
"print(\" Tools denied conditionally: web_search\\n\")\n",
|
||||
"\n",
|
||||
"print(\"✅ All policies ready!\")"
|
||||
"print(\"\u2705 All policies ready!\")"
|
||||
]
|
||||
},
|
||||
{
|
||||
@@ -776,7 +817,7 @@
|
||||
"role_name = role_arn.split('/')[-1] \n",
|
||||
"\n",
|
||||
"iam_client = boto3.client('iam')\n",
|
||||
"print(\"🔧 Updating Gateway IAM role with Policy Engine permissions...\")\n",
|
||||
"print(\"\ud83d\udd27 Updating Gateway IAM role with Policy Engine permissions...\")\n",
|
||||
"\n",
|
||||
"# Policy document that grants access to Policy Engine\n",
|
||||
"policy_document = {\n",
|
||||
@@ -803,16 +844,16 @@
|
||||
" PolicyDocument=json.dumps(policy_document)\n",
|
||||
" )\n",
|
||||
" \n",
|
||||
" print(f\"✅ IAM role updated successfully\")\n",
|
||||
" print(f\"\u2705 IAM role updated successfully\")\n",
|
||||
" print(f\" Role: {role_name}\")\n",
|
||||
" print(f\" Added permissions: GetPolicyEngine, GetPolicy, ListPolicies\")\n",
|
||||
" print(\"\\n⏳ Waiting 10 seconds for IAM changes to propagate...\")\n",
|
||||
" print(\"\\n\u23f3 Waiting 10 seconds for IAM changes to propagate...\")\n",
|
||||
" time.sleep(10)\n",
|
||||
" \n",
|
||||
" print(\"✅ Ready to attach Policy Engine\")\n",
|
||||
" print(\"\u2705 Ready to attach Policy Engine\")\n",
|
||||
" \n",
|
||||
"except Exception as e:\n",
|
||||
" print(f\"❌ Error updating IAM role: {e}\")\n",
|
||||
" print(f\"\u274c Error updating IAM role: {e}\")\n",
|
||||
" print(\"\\nYou may need to manually add these permissions to the role.\")"
|
||||
]
|
||||
},
|
||||
@@ -838,7 +879,7 @@
|
||||
"# Initialize gateway client\n",
|
||||
"gateway_client_toolkit = GatewayClient(region_name=REGION)\n",
|
||||
"\n",
|
||||
"print(\"🔧 Attaching Policy Engine to Gateway...\")\n",
|
||||
"print(\"\ud83d\udd27 Attaching Policy Engine to Gateway...\")\n",
|
||||
"print(f\" Mode: ENFORCE (policies will block unauthorized requests)\\n\")\n",
|
||||
"\n",
|
||||
"# Attach the policy engine to the gateway\n",
|
||||
@@ -848,11 +889,11 @@
|
||||
" mode=\"ENFORCE\"\n",
|
||||
")\n",
|
||||
"\n",
|
||||
"print(\"✅ Policy Engine attached successfully!\")\n",
|
||||
"print(\"\u2705 Policy Engine attached successfully!\")\n",
|
||||
"print(f\" Gateway ID: {gateway['id']}\")\n",
|
||||
"print(f\" Policy Engine: {engine['policyEngineId']}\")\n",
|
||||
"print(f\" Mode: ENFORCE\")\n",
|
||||
"print(\"\\n🔒 Authorization is now active!\")"
|
||||
"print(\"\\n\ud83d\udd12 Authorization is now active!\")"
|
||||
]
|
||||
},
|
||||
{
|
||||
@@ -893,7 +934,7 @@
|
||||
"# Run the tests\n",
|
||||
"test_agent_responses(test_prompts)\n",
|
||||
"\n",
|
||||
"print(\"\\\\n✅ Policy testing completed!\")"
|
||||
"print(\"\\\\n\u2705 Policy testing completed!\")"
|
||||
]
|
||||
},
|
||||
{
|
||||
@@ -901,7 +942,7 @@
|
||||
"id": "81ab1e33-04ae-4469-91d5-e85a0a0e4070",
|
||||
"metadata": {},
|
||||
"source": [
|
||||
"### Congratulations! 🎉\n",
|
||||
"### Congratulations! \ud83c\udf89\n",
|
||||
"\n",
|
||||
"\n",
|
||||
"You have successfully completed Lab 3: Securely connect tools to your Agent with AgentCore Gateway\n",
|
||||
@@ -968,4 +1009,4 @@
|
||||
},
|
||||
"nbformat": 4,
|
||||
"nbformat_minor": 5
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user