[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"skill-cc005fdb-544d-4311-856e-23f6bd4da8e5":3,"$fzHNRFjW__8ra00jsSa8g9DizCjnqfwyvJh0yjfo97uo":43},{"id":4,"title":5,"description":6,"categoryId":7,"moduleId":8,"tags":9,"prompt":10,"icon":11,"source":12,"sourceUrl":13,"authorId":14,"authorName":15,"isPublic":16,"stars":17,"runs":18,"createdAt":19,"updatedAt":19,"module":20,"category":27,"packages":34},"cc005fdb-544d-4311-856e-23f6bd4da8e5","aws-cost-cleanup","自动清理未使用的AWS资源以降低成本","cat_coding_devops","mod_coding","sickn33,coding","---\nname: aws-cost-cleanup\ndescription: \"Automated cleanup of unused AWS resources to reduce costs\"\nrisk: safe\nsource: community\ndate_added: \"2026-02-27\"\n---\n\n# AWS Cost Cleanup\n\nAutomate the identification and removal of unused AWS resources to eliminate waste.\n\n## When to Use This Skill\n\nUse this skill when you need to automatically clean up unused AWS resources to reduce costs and eliminate waste.\n\n## Automated Cleanup Targets\n\n**Storage**\n- Unattached EBS volumes\n- Old EBS snapshots (>90 days)\n- Incomplete multipart S3 uploads\n- Old S3 versions in versioned buckets\n\n**Compute**\n- Stopped EC2 instances (>30 days)\n- Unused AMIs and associated snapshots\n- Unused Elastic IPs\n\n**Networking**\n- Unused Elastic Load Balancers\n- Unused NAT Gateways\n- Orphaned ENIs\n\n## Cleanup Scripts\n\n### Safe Cleanup (Dry-Run First)\n\n```bash\n#!\u002Fbin\u002Fbash\n# cleanup-unused-ebs.sh\n\necho \"Finding unattached EBS volumes...\"\nVOLUMES=$(aws ec2 describe-volumes \\\n  --filters Name=status,Values=available \\\n  --query 'Volumes[*].VolumeId' \\\n  --output text)\n\nfor vol in $VOLUMES; do\n  echo \"Would delete: $vol\"\n  # Uncomment to actually delete:\n  # aws ec2 delete-volume --volume-id $vol\ndone\n```\n\n```bash\n#!\u002Fbin\u002Fbash\n# cleanup-old-snapshots.sh\n\nCUTOFF_DATE=$(date -d '90 days ago' --iso-8601)\n\naws ec2 describe-snapshots --owner-ids self \\\n  --query \"Snapshots[?StartTime\u003C='$CUTOFF_DATE'].[SnapshotId,StartTime,VolumeSize]\" \\\n  --output text | while read snap_id start_time size; do\n  \n  echo \"Snapshot: $snap_id (Created: $start_time, Size: ${size}GB)\"\n  # Uncomment to delete:\n  # aws ec2 delete-snapshot --snapshot-id $snap_id\ndone\n```\n\n```bash\n#!\u002Fbin\u002Fbash\n# release-unused-eips.sh\n\naws ec2 describe-addresses \\\n  --query 'Addresses[?AssociationId==null].[AllocationId,PublicIp]' \\\n  --output text | while read alloc_id public_ip; do\n  \n  echo \"Would release: $public_ip ($alloc_id)\"\n  # Uncomment to release:\n  # aws ec2 release-address --allocation-id $alloc_id\ndone\n```\n\n### S3 Lifecycle Automation\n\n```bash\n# Apply lifecycle policy to transition old objects to cheaper storage\ncat > lifecycle-policy.json \u003C\u003CEOF\n{\n  \"Rules\": [\n    {\n      \"Id\": \"Archive old objects\",\n      \"Status\": \"Enabled\",\n      \"Transitions\": [\n        {\n          \"Days\": 90,\n          \"StorageClass\": \"STANDARD_IA\"\n        },\n        {\n          \"Days\": 180,\n          \"StorageClass\": \"GLACIER\"\n        }\n      ],\n      \"NoncurrentVersionExpiration\": {\n        \"NoncurrentDays\": 30\n      },\n      \"AbortIncompleteMultipartUpload\": {\n        \"DaysAfterInitiation\": 7\n      }\n    }\n  ]\n}\nEOF\n\naws s3api put-bucket-lifecycle-configuration \\\n  --bucket my-bucket \\\n  --lifecycle-configuration file:\u002F\u002Flifecycle-policy.json\n```\n\n## Cost Impact Calculator\n\n```python\n#!\u002Fusr\u002Fbin\u002Fenv python3\n# calculate-savings.py\n\nimport boto3\nfrom datetime import datetime, timedelta\n\nec2 = boto3.client('ec2')\n\n# Calculate EBS volume savings\nvolumes = ec2.describe_volumes(\n    Filters=[{'Name': 'status', 'Values': ['available']}]\n)\n\ntotal_size = sum(v['Size'] for v in volumes['Volumes'])\nmonthly_cost = total_size * 0.10  # $0.10\u002FGB-month for gp3\n\nprint(f\"Unattached EBS Volumes: {len(volumes['Volumes'])}\")\nprint(f\"Total Size: {total_size} GB\")\nprint(f\"Monthly Savings: ${monthly_cost:.2f}\")\n\n# Calculate Elastic IP savings\naddresses = ec2.describe_addresses()\nunused = [a for a in addresses['Addresses'] if 'AssociationId' not in a]\n\neip_cost = len(unused) * 3.65  # $0.005\u002Fhour * 730 hours\nprint(f\"\\nUnused Elastic IPs: {len(unused)}\")\nprint(f\"Monthly Savings: ${eip_cost:.2f}\")\n\nprint(f\"\\nTotal Monthly Savings: ${monthly_cost + eip_cost:.2f}\")\nprint(f\"Annual Savings: ${(monthly_cost + eip_cost) * 12:.2f}\")\n```\n\n## Automated Cleanup Lambda\n\n```python\nimport boto3\nfrom datetime import datetime, timedelta\n\ndef lambda_handler(event, context):\n    ec2 = boto3.client('ec2')\n    \n    # Delete unattached volumes older than 7 days\n    volumes = ec2.describe_volumes(\n        Filters=[{'Name': 'status', 'Values': ['available']}]\n    )\n    \n    cutoff = datetime.now() - timedelta(days=7)\n    deleted = 0\n    \n    for vol in volumes['Volumes']:\n        create_time = vol['CreateTime'].replace(tzinfo=None)\n        if create_time \u003C cutoff:\n            try:\n                ec2.delete_volume(VolumeId=vol['VolumeId'])\n                deleted += 1\n                print(f\"Deleted volume: {vol['VolumeId']}\")\n            except Exception as e:\n                print(f\"Error deleting {vol['VolumeId']}: {e}\")\n    \n    return {\n        'statusCode': 200,\n        'body': f'Deleted {deleted} volumes'\n    }\n```\n\n## Cleanup Workflow\n\n1. **Discovery Phase** (Read-only)\n   - Run all describe commands\n   - Generate cost impact report\n   - Review with team\n\n2. **Validation Phase**\n   - Verify resources are truly unused\n   - Check for dependencies\n   - Notify resource owners\n\n3. **Execution Phase** (Dry-run first)\n   - Run cleanup scripts with dry-run\n   - Review proposed changes\n   - Execute actual cleanup\n\n4. **Verification Phase**\n   - Confirm deletions\n   - Monitor for issues\n   - Document savings\n\n## Safety Checklist\n\n- [ ] Run in dry-run mode first\n- [ ] Verify resources have no dependencies\n- [ ] Check resource tags for ownership\n- [ ] Notify stakeholders before deletion\n- [ ] Create snapshots of critical data\n- [ ] Test in non-production first\n- [ ] Have rollback plan ready\n- [ ] Document all deletions\n\n## Example Prompts\n\n**Discovery**\n- \"Find all unused resources and calculate potential savings\"\n- \"Generate a cleanup report for my AWS account\"\n- \"What resources can I safely delete?\"\n\n**Execution**\n- \"Create a script to cleanup unattached EBS volumes\"\n- \"Delete all snapshots older than 90 days\"\n- \"Release unused Elastic IPs\"\n\n**Automation**\n- \"Set up automated cleanup for old snapshots\"\n- \"Create a Lambda function for weekly cleanup\"\n- \"Schedule monthly resource cleanup\"\n\n## Integration with AWS Organizations\n\n```bash\n# Run cleanup across multiple accounts\nfor account in $(aws organizations list-accounts \\\n  --query 'Accounts[*].Id' --output text); do\n  \n  echo \"Checking account: $account\"\n  aws ec2 describe-volumes \\\n    --filters Name=status,Values=available \\\n    --profile account-$account\ndone\n```\n\n## Monitoring and Alerts\n\n```bash\n# Create CloudWatch alarm for cost anomalies\naws cloudwatch put-metric-alarm \\\n  --alarm-name high-cost-alert \\\n  --alarm-description \"Alert when daily cost exceeds threshold\" \\\n  --metric-name EstimatedCharges \\\n  --namespace AWS\u002FBilling \\\n  --statistic Maximum \\\n  --period 86400 \\\n  --evaluation-periods 1 \\\n  --threshold 100 \\\n  --comparison-operator GreaterThanThreshold\n```\n\n## Best Practices\n\n- Schedule cleanup during maintenance windows\n- Always create final snapshots before deletion\n- Use resource tags to identify cleanup candidates\n- Implement approval workflow for production\n- Log all cleanup actions for audit\n- Set up cost anomaly detection\n- Review cleanup results weekly\n\n## Risk Mitigation\n\n**Medium Risk Actions:**\n- Deleting unattached volumes (ensure no planned reattachment)\n- Removing old snapshots (verify no compliance requirements)\n- Releasing Elastic IPs (check DNS records)\n\n**Always:**\n- Maintain 30-day backup retention\n- Use AWS Backup for critical resources\n- Test restore procedures\n- Document cleanup decisions\n\n## Kiro CLI Integration\n\n```bash\n# Analyze and cleanup in one command\nkiro-cli chat \"Use aws-cost-cleanup to find and remove unused resources\"\n\n# Generate cleanup script\nkiro-cli chat \"Create a safe cleanup script for my AWS account\"\n\n# Schedule automated cleanup\nkiro-cli chat \"Set up weekly automated cleanup using aws-cost-cleanup\"\n```\n\n## Additional Resources\n\n- [AWS Resource Cleanup Best Practices](https:\u002F\u002Faws.amazon.com\u002Fblogs\u002Fmt\u002Fautomate-resource-cleanup\u002F)\n- [AWS Systems Manager Automation](https:\u002F\u002Fdocs.aws.amazon.com\u002Fsystems-manager\u002Flatest\u002Fuserguide\u002Fsystems-manager-automation.html)\n- [AWS Config Rules for Compliance](https:\u002F\u002Fdocs.aws.amazon.com\u002Fconfig\u002Flatest\u002Fdeveloperguide\u002Fmanaged-rules-by-aws-config.html)\n\n## Limitations\n- Use this skill only when the task clearly matches the scope described above.\n- Do not treat the output as a substitute for environment-specific validation, testing, or expert review.\n- Stop and ask for clarification if required inputs, permissions, safety boundaries, or success criteria are missing.\n","","imported","https:\u002F\u002Fgithub.com\u002Fsickn33\u002Fantigravity-awesome-skills","user_system_seed","SkillOPIC",true,126,1390,"2026-05-16 13:04:48",{"id":8,"name":21,"slug":22,"icon":23,"description":24,"sort":25,"createdAt":26},"编程开发","coding","mdi-code-braces","代码生成、调试、审查，提升开发效率",2,"2026-05-16 12:53:40",{"id":7,"name":28,"slug":29,"icon":30,"description":31,"moduleId":8,"sort":32,"skillCount":33,"createdAt":26},"DevOps","devops","mdi-cog-outline","CI\u002FCD、容器化、部署运维",3,162,[35],{"id":36,"skillId":4,"version":37,"fileName":38,"fileSize":39,"filePath":40,"fileHash":41,"manifest":42,"createdAt":19},"2c893c88-cf6a-4ff1-a029-2cd7245c0189","1.0.0","aws-cost-cleanup.zip",3497,"uploads\u002Fskills\u002Fcc005fdb-544d-4311-856e-23f6bd4da8e5\u002Faws-cost-cleanup.zip","97a3f04922fb1b45227c79d87a669d1f06b21a7a6622b50ce8bd1aae8ae36b9c","[{\"path\":\"SKILL.md\",\"isDirectory\":false,\"size\":8300}]",{"code":44,"message":45,"data":46},200,"success",{"items":47,"stats":48,"page":51},[],{"averageRating":49,"totalRatings":49,"ratingCounts":50},0,[49,49,49,49,49],{"limit":52,"offset":49,"hasMore":53,"nextOffset":52,"ratedOnly":16},15,false]