背景
AWS WAF(Web Application Firewall)是亚马逊网络服务(AWS)提供的一项安全服务,用于保护应用程序免受常见的网络威胁,如跨站脚本(XSS)、SQL注入、跨站请求伪造(CSRF)等。它通过检测和阻止恶意请求,实时监控和灵活的规则设置,提供了全面的应用程序防护。
AWS WAF的功能和必要性
- 防护应用程序: AWS WAF可以根据预定义的规则或自定义规则来过滤和阻止请求,有效地保护应用程序免受各种网络威胁。
- 实时监控和日志记录: 提供实时监控和日志记录功能,有助于及时发现和应对潜在的网络威胁。记录所有请求和响应数据,生成详细的日志供审计和分析使用。
- 灵活的规则设置: 允许用户根据自身需求设置规则,适应不同的应用程序和网络威胁场景。支持预定义规则和自定义规则,提供高度灵活性。
- 高可用性和可扩展性: 作为基于云的服务,AWS WAF具有高可用性和可扩展性,能够自动处理大量的请求流量,并根据需要进行水平扩展。
开发WAF批量添加ALB防护的功能的好处
- 提高效率: 批量添加ALB防护功能可以帮助用户快速、批量地将WAF规则应用到多个应用程序中,从而提高配置的效率。通过一次性的批量操作,用户无需逐个手动添加规则。
- 降低错误率: 批量添加功能可以减少人工操作的错误率。相比手动添加,批量添加可以减少因疏忽或错误而导致的规则配置错误,提高安全性。
- 简化管理: 批量添加功能可以简化WAF规则的管理。用户可以通过一次性的批量操作来添加、更新或删除规则,而无需逐个操作,从而减少了管理的复杂性。
前提
- 已经在us-east-1安装区域WAF功能。
- 提前设置好本地开发环境AK/SK。
开发环境
- Python 3.8.2
安装依赖包
pip install boto3==1.26.105
用户权限
用户需要以下权限:
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "VisualEditor0",
"Effect": "Allow",
"Action": [
"wafv2:ListResourcesForWebACL",
"cloudwatch:PutMetricAlarm",
"shield:AssociateHealthCheck",
"elasticloadbalancing:DescribeLoadBalancers",
"wafv2:ListWebACLs",
"wafv2:AssociateWebACL",
"route53:CreateHealthCheck",
"shield:CreateProtection",
"shield:EnableApplicationLayerAutomaticResponse",
"shield:ListProtections",
"apigateway:SetWebACL",
"apigateway:GET",
"iam:GetRole",
"elasticloadbalancing:SetWebACL"
],
"Resource": "*"
}
]
}
WAF批量添加ALB防护
以下Python脚本实现了对外部提供服务的ALB批量添加WAF防护的功能。新增保护返回状态码200,空白说明已经受到保护。
import boto3
# 获取所有WAFv2WebACL的ARN
def get_wafv2_web_acl_arns():
wafv2 = boto3.client('wafv2', region_name='us-east-1')
response = wafv2.list_web_acls(Scope='REGIONAL')
web_acl_arns = [web_acl['ARN'] for web_acl in response['WebACLs']]
return web_acl_arns
# 获取所有应用类型的负载均衡器的ARN
def get_load_balancer_arns():
elbv2 = boto3.client('elbv2', region_name='us-east-1')
response = elbv2.describe_load_balancers()
load_balancer_arns = [lb['LoadBalancerArn'] for lb in response['LoadBalancers'] if lb['Type'] == 'application' and not lb['Scheme'] == 'internal']
return load_balancer_arns
# 将WAFACL与ALB关联
def associate_waf_acl_with_alb(web_acl_arn, alb_arn):
wafv2 = boto3.client('wafv2')
response = wafv2.associate_web_acl(
WebACLArn=web_acl_arn,
ResourceArn=alb_arn
)
return response
# 检查ALB是否与WAF关联
def is_alb_protected(alb_arn, web_acl_arn):
wafv2 = boto3.client('wafv2', region_name='us-east-1')
response = wafv2.list_resources_for_web_acl(WebACLArn=web_acl_arn)
protected_resources = response['ResourceArns']
return alb_arn in protected_resources
# 使用示例
web_acl_arns = get_wafv2_web_acl_arns()
load_balancer_arns = get_load_balancer_arns()
for alb_arn in load_balancer_arns:
for web_acl_arn in web_acl_arns:
value = is_alb_protected(alb_arn, web_acl_arn)
if not value:
response = associate_waf_acl_with_alb(web_acl_arn, alb_arn)
print(response["ResponseMetadata"]["HTTPStatusCode"])
WAF批量移除ALB防护
以下Python脚本实现了WAF批量移除ALB
以下详解权限没有单独验证,笔者是使用管理员实现,移除返回状态200,空白说明没有可移除
import boto3 # 导入boto3库,用于与AWS服务进行交互
def get_load_balancer_arns(): # 定义获取负载均衡器ARN的函数
elbv2 = boto3.client('elbv2', region_name='us-east-1') # 创建elbv2客户端对象
response = elbv2.describe_load_balancers() # 调用describe_load_balancers方法获取负载均衡器信息
load_balancer_arns = [lb['LoadBalancerArn'] for lb in response['LoadBalancers'] if lb['Type'] == 'application' and not lb['Scheme'] == 'internal'] # 提取符合条件的负载均衡器ARN
return load_balancer_arns # 返回负载均衡器ARN列表
def get_wafv2_web_acl_arns(): # 定义获取WAFv2 Web ACL ARN的函数
wafv2 = boto3.client('wafv2', region_name='us-east-1') # 创建wafv2客户端对象
response = wafv2.list_web_acls(Scope='REGIONAL') # 调用list_web_acls方法获取Web ACL信息
web_acl_arns = [web_acl['ARN'] for web_acl in response['WebACLs']] # 提取Web ACL ARN
return web_acl_arns # 返回Web ACL ARN列表
def disassociate_web_acl(resource_arn): # 定义取消关联Web ACL的函数
wafv2 = boto3.client('wafv2') # 创建wafv2客户端对象
response = wafv2.disassociate_web_acl(ResourceArn=resource_arn) # 调用disassociate_web_acl方法取消关联Web ACL
return response # 返回取消关联操作的响应
def is_alb_protected(alb_arn, web_acl_arn): # 定义判断负载均衡器是否受到保护的函数
wafv2 = boto3.client('wafv2', region_name='us-east-1') # 创建wafv2客户端对象
response = wafv2.list_resources_for_web_acl(WebACLArn=web_acl_arn) # 调用list_resources_for_web_acl方法获取与Web ACL关联的资源
protected_resources = response['ResourceArns'] # 提取受保护的资源ARN列表
return alb_arn in protected_resources # 判断负载均衡器ARN是否在受保护的资源列表中
# 使用示例
load_balancer_arns = get_load_balancer_arns() # 获取负载均衡器ARN列表
web_acl_arns = get_wafv2_web_acl_arns() # 获取Web ACL ARN列表
for resource_arn in load_balancer_arns: # 遍历负载均衡器ARN列表
for web_acl_arn in web_acl_arns: # 遍历Web ACL ARN列表
value = is_alb_protected(resource_arn, web_acl_arn) # 判断负载均衡器是否受到保护
if value: # 如果受到保护
response = disassociate_web_acl(resource_arn) # 取消关联Web ACL
print(response["ResponseMetadata"]["HTTPStatusCode"]) # 打印取消关联操作的HTTP状态码