aws-cis-controls-assessment 1.0.8__py3-none-any.whl → 1.0.10__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (30) hide show
  1. aws_cis_assessment/__init__.py +1 -1
  2. aws_cis_assessment/config/rules/cis_controls_ig1.yaml +94 -1
  3. aws_cis_assessment/config/rules/cis_controls_ig2.yaml +83 -1
  4. aws_cis_assessment/controls/ig1/__init__.py +17 -0
  5. aws_cis_assessment/controls/ig1/control_aws_backup_service.py +1276 -0
  6. aws_cis_assessment/controls/ig2/__init__.py +12 -0
  7. aws_cis_assessment/controls/ig2/control_aws_backup_ig2.py +23 -0
  8. aws_cis_assessment/core/assessment_engine.py +24 -0
  9. aws_cis_assessment/core/models.py +1 -0
  10. aws_cis_assessment/core/scoring_engine.py +30 -0
  11. aws_cis_assessment/reporters/base_reporter.py +2 -0
  12. aws_cis_assessment/reporters/html_reporter.py +279 -7
  13. {aws_cis_controls_assessment-1.0.8.dist-info → aws_cis_controls_assessment-1.0.10.dist-info}/METADATA +57 -10
  14. {aws_cis_controls_assessment-1.0.8.dist-info → aws_cis_controls_assessment-1.0.10.dist-info}/RECORD +30 -24
  15. docs/README.md +14 -3
  16. docs/adding-aws-backup-controls.md +562 -0
  17. docs/assessment-logic.md +291 -3
  18. docs/cli-reference.md +1 -1
  19. docs/config-rule-mappings.md +46 -5
  20. docs/developer-guide.md +312 -3
  21. docs/dual-scoring-implementation.md +303 -0
  22. docs/installation.md +2 -2
  23. docs/scoring-comparison-aws-config.md +379 -0
  24. docs/scoring-methodology.md +350 -0
  25. docs/troubleshooting.md +211 -2
  26. docs/user-guide.md +47 -2
  27. {aws_cis_controls_assessment-1.0.8.dist-info → aws_cis_controls_assessment-1.0.10.dist-info}/WHEEL +0 -0
  28. {aws_cis_controls_assessment-1.0.8.dist-info → aws_cis_controls_assessment-1.0.10.dist-info}/entry_points.txt +0 -0
  29. {aws_cis_controls_assessment-1.0.8.dist-info → aws_cis_controls_assessment-1.0.10.dist-info}/licenses/LICENSE +0 -0
  30. {aws_cis_controls_assessment-1.0.8.dist-info → aws_cis_controls_assessment-1.0.10.dist-info}/top_level.txt +0 -0
docs/assessment-logic.md CHANGED
@@ -5,7 +5,7 @@ This document provides detailed information about the assessment logic used by t
5
5
  ## Production Framework Overview
6
6
 
7
7
  **✅ Complete Implementation Status**
8
- - 136 AWS Config rules implemented (131 CIS Controls + 5 bonus)
8
+ - 138 AWS Config rules implemented (133 CIS Controls + 5 bonus)
9
9
  - 100% coverage across all Implementation Groups (IG1, IG2, IG3)
10
10
  - Production-tested with enterprise-grade error handling
11
11
  - Optimized for large-scale enterprise deployments
@@ -25,7 +25,7 @@ This document provides detailed information about the assessment logic used by t
25
25
 
26
26
  The assessment tool evaluates AWS account configurations against CIS Controls using the same logic as AWS Config rules, but without requiring AWS Config to be enabled. Each assessment follows a standardized process while implementing control-specific evaluation logic.
27
27
 
28
- **Framework Scope**: 136 implemented rules covering all CIS Controls requirements plus 5 bonus security enhancements for additional value.
28
+ **Framework Scope**: 138 implemented rules covering all CIS Controls requirements plus 5 bonus security enhancements for additional value.
29
29
 
30
30
  ### Key Principles
31
31
 
@@ -763,4 +763,292 @@ def batch_evaluate_resources(self, resources, batch_size=50):
763
763
  return results
764
764
  ```
765
765
 
766
- This comprehensive assessment logic ensures accurate, efficient, and reliable evaluation of AWS resources against CIS Controls while maintaining compatibility with AWS Config rule specifications.
766
+ This comprehensive assessment logic ensures accurate, efficient, and reliable evaluation of AWS resources against CIS Controls while maintaining compatibility with AWS Config rule specifications.
767
+
768
+
769
+ ### AWS Backup Resources
770
+ ```python
771
+ def discover_backup_plans(self, backup_client, region):
772
+ """Discover AWS Backup plans in specific region."""
773
+ try:
774
+ paginator = backup_client.get_paginator('list_backup_plans')
775
+
776
+ backup_plans = []
777
+ for page in paginator.paginate():
778
+ for plan in page['BackupPlansList']:
779
+ try:
780
+ # Get detailed plan information
781
+ plan_details = backup_client.get_backup_plan(
782
+ BackupPlanId=plan['BackupPlanId']
783
+ )
784
+
785
+ backup_plans.append({
786
+ 'BackupPlanId': plan['BackupPlanId'],
787
+ 'BackupPlanName': plan['BackupPlanName'],
788
+ 'BackupPlanArn': plan['BackupPlanArn'],
789
+ 'CreationDate': plan['CreationDate'],
790
+ 'VersionId': plan['VersionId'],
791
+ 'Rules': plan_details['BackupPlan'].get('Rules', []),
792
+ 'Region': region
793
+ })
794
+
795
+ except ClientError as e:
796
+ # Skip plans we can't access
797
+ if e.response['Error']['Code'] in ['AccessDenied', 'ResourceNotFoundException']:
798
+ continue
799
+ raise
800
+
801
+ return backup_plans
802
+
803
+ except ClientError as e:
804
+ if e.response['Error']['Code'] == 'AccessDenied':
805
+ self.logger.warning(f"Insufficient permissions for Backup in {region}")
806
+ return []
807
+ raise
808
+
809
+ def discover_backup_vaults(self, backup_client, region):
810
+ """Discover AWS Backup vaults in specific region."""
811
+ try:
812
+ paginator = backup_client.get_paginator('list_backup_vaults')
813
+
814
+ backup_vaults = []
815
+ for page in paginator.paginate():
816
+ for vault in page['BackupVaultList']:
817
+ try:
818
+ # Get vault access policy if exists
819
+ try:
820
+ policy_response = backup_client.get_backup_vault_access_policy(
821
+ BackupVaultName=vault['BackupVaultName']
822
+ )
823
+ vault['Policy'] = policy_response.get('Policy')
824
+ except ClientError as e:
825
+ if e.response['Error']['Code'] == 'ResourceNotFoundException':
826
+ vault['Policy'] = None
827
+ else:
828
+ raise
829
+
830
+ backup_vaults.append({
831
+ 'BackupVaultName': vault['BackupVaultName'],
832
+ 'BackupVaultArn': vault['BackupVaultArn'],
833
+ 'CreationDate': vault['CreationDate'],
834
+ 'EncryptionKeyArn': vault.get('EncryptionKeyArn'),
835
+ 'NumberOfRecoveryPoints': vault.get('NumberOfRecoveryPoints', 0),
836
+ 'Policy': vault.get('Policy'),
837
+ 'Region': region
838
+ })
839
+
840
+ except ClientError as e:
841
+ if e.response['Error']['Code'] in ['AccessDenied', 'ResourceNotFoundException']:
842
+ continue
843
+ raise
844
+
845
+ return backup_vaults
846
+
847
+ except ClientError as e:
848
+ if e.response['Error']['Code'] == 'AccessDenied':
849
+ self.logger.warning(f"Insufficient permissions for Backup vaults in {region}")
850
+ return []
851
+ raise
852
+ ```
853
+
854
+ ## AWS Backup Controls Logic
855
+
856
+ ### Backup Plan Frequency and Retention Check
857
+
858
+ Evaluates backup plans to ensure they meet minimum frequency and retention requirements:
859
+
860
+ ```python
861
+ def evaluate_backup_plan_compliance(self, resource, aws_factory):
862
+ """Evaluate backup plan frequency and retention requirements."""
863
+ backup_plan_id = resource['BackupPlanId']
864
+ backup_plan_name = resource['BackupPlanName']
865
+ rules = resource.get('Rules', [])
866
+ region = resource['Region']
867
+
868
+ if not rules:
869
+ return ComplianceResult(
870
+ resource_id=backup_plan_id,
871
+ resource_type="AWS::Backup::BackupPlan",
872
+ compliance_status="NON_COMPLIANT",
873
+ evaluation_reason="Backup plan has no rules defined",
874
+ config_rule_name="backup-plan-min-frequency-and-min-retention-check",
875
+ region=region,
876
+ timestamp=datetime.now(),
877
+ remediation_guidance="Add backup rules with appropriate frequency and retention"
878
+ )
879
+
880
+ # Check each rule for compliance
881
+ non_compliant_rules = []
882
+
883
+ for rule in rules:
884
+ rule_name = rule.get('RuleName', 'Unnamed')
885
+
886
+ # Check frequency (schedule expression)
887
+ schedule = rule.get('ScheduleExpression', '')
888
+ if not self._meets_frequency_requirement(schedule):
889
+ non_compliant_rules.append(
890
+ f"{rule_name}: frequency does not meet minimum (daily)"
891
+ )
892
+
893
+ # Check retention (minimum 35 days / 5 weeks)
894
+ lifecycle = rule.get('Lifecycle', {})
895
+ delete_after_days = lifecycle.get('DeleteAfterDays')
896
+
897
+ if delete_after_days is None or delete_after_days < 35:
898
+ non_compliant_rules.append(
899
+ f"{rule_name}: retention {delete_after_days} days is less than minimum (35 days)"
900
+ )
901
+
902
+ if non_compliant_rules:
903
+ return ComplianceResult(
904
+ resource_id=backup_plan_id,
905
+ resource_type="AWS::Backup::BackupPlan",
906
+ compliance_status="NON_COMPLIANT",
907
+ evaluation_reason=f"Backup plan rules do not meet requirements: {'; '.join(non_compliant_rules)}",
908
+ config_rule_name="backup-plan-min-frequency-and-min-retention-check",
909
+ region=region,
910
+ timestamp=datetime.now(),
911
+ remediation_guidance="Update backup plan rules to meet minimum frequency (daily) and retention (35 days)"
912
+ )
913
+
914
+ return ComplianceResult(
915
+ resource_id=backup_plan_id,
916
+ resource_type="AWS::Backup::BackupPlan",
917
+ compliance_status="COMPLIANT",
918
+ evaluation_reason="Backup plan meets frequency and retention requirements",
919
+ config_rule_name="backup-plan-min-frequency-and-min-retention-check",
920
+ region=region,
921
+ timestamp=datetime.now()
922
+ )
923
+
924
+ def _meets_frequency_requirement(self, schedule_expression):
925
+ """Check if schedule expression meets minimum daily frequency."""
926
+ if not schedule_expression:
927
+ return False
928
+
929
+ # Check for rate expressions (e.g., "rate(1 day)")
930
+ if schedule_expression.startswith('rate('):
931
+ # Extract number and unit
932
+ match = re.match(r'rate\((\d+)\s+(hour|day|week)\)', schedule_expression)
933
+ if match:
934
+ value = int(match.group(1))
935
+ unit = match.group(2)
936
+
937
+ # Convert to hours for comparison
938
+ if unit == 'hour':
939
+ hours = value
940
+ elif unit == 'day':
941
+ hours = value * 24
942
+ elif unit == 'week':
943
+ hours = value * 24 * 7
944
+
945
+ # Must be at least daily (24 hours or less)
946
+ return hours <= 24
947
+
948
+ # Check for cron expressions (e.g., "cron(0 0 * * ? *)")
949
+ elif schedule_expression.startswith('cron('):
950
+ # Daily or more frequent cron patterns
951
+ # This is a simplified check - full cron parsing would be more complex
952
+ return True # Assume cron expressions are configured appropriately
953
+
954
+ return False
955
+ ```
956
+
957
+ ### Backup Vault Access Policy Check
958
+
959
+ Evaluates backup vault access policies to ensure they don't allow overly permissive access:
960
+
961
+ ```python
962
+ def evaluate_backup_vault_policy(self, resource, aws_factory):
963
+ """Evaluate backup vault access policy for security."""
964
+ vault_name = resource['BackupVaultName']
965
+ vault_arn = resource['BackupVaultArn']
966
+ policy = resource.get('Policy')
967
+ region = resource['Region']
968
+
969
+ # If no policy, vault is secure by default
970
+ if not policy:
971
+ return ComplianceResult(
972
+ resource_id=vault_arn,
973
+ resource_type="AWS::Backup::BackupVault",
974
+ compliance_status="COMPLIANT",
975
+ evaluation_reason="Backup vault has no access policy (secure by default)",
976
+ config_rule_name="backup-vault-access-policy-check",
977
+ region=region,
978
+ timestamp=datetime.now()
979
+ )
980
+
981
+ try:
982
+ # Parse policy JSON
983
+ policy_doc = json.loads(policy) if isinstance(policy, str) else policy
984
+
985
+ # Check for overly permissive principals
986
+ security_issues = []
987
+
988
+ for statement in policy_doc.get('Statement', []):
989
+ principal = statement.get('Principal', {})
990
+ effect = statement.get('Effect', '')
991
+
992
+ # Check for wildcard principals with Allow effect
993
+ if effect == 'Allow':
994
+ if principal == '*' or principal == {'AWS': '*'}:
995
+ security_issues.append("Policy allows access from any principal (*)")
996
+
997
+ # Check for overly broad actions
998
+ actions = statement.get('Action', [])
999
+ if isinstance(actions, str):
1000
+ actions = [actions]
1001
+
1002
+ if 'backup:*' in actions or '*' in actions:
1003
+ security_issues.append("Policy allows all backup actions (*)")
1004
+
1005
+ if security_issues:
1006
+ return ComplianceResult(
1007
+ resource_id=vault_arn,
1008
+ resource_type="AWS::Backup::BackupVault",
1009
+ compliance_status="NON_COMPLIANT",
1010
+ evaluation_reason=f"Backup vault policy has security issues: {'; '.join(security_issues)}",
1011
+ config_rule_name="backup-vault-access-policy-check",
1012
+ region=region,
1013
+ timestamp=datetime.now(),
1014
+ remediation_guidance="Update vault policy to restrict access to specific principals and actions"
1015
+ )
1016
+
1017
+ return ComplianceResult(
1018
+ resource_id=vault_arn,
1019
+ resource_type="AWS::Backup::BackupVault",
1020
+ compliance_status="COMPLIANT",
1021
+ evaluation_reason="Backup vault policy follows security best practices",
1022
+ config_rule_name="backup-vault-access-policy-check",
1023
+ region=region,
1024
+ timestamp=datetime.now()
1025
+ )
1026
+
1027
+ except (json.JSONDecodeError, KeyError) as e:
1028
+ return ComplianceResult(
1029
+ resource_id=vault_arn,
1030
+ resource_type="AWS::Backup::BackupVault",
1031
+ compliance_status="ERROR",
1032
+ evaluation_reason=f"Failed to parse vault policy: {str(e)}",
1033
+ config_rule_name="backup-vault-access-policy-check",
1034
+ region=region,
1035
+ timestamp=datetime.now(),
1036
+ remediation_guidance="Verify vault policy is valid JSON"
1037
+ )
1038
+ ```
1039
+
1040
+ ### Backup Controls Integration
1041
+
1042
+ The AWS Backup service-level controls complement the existing resource-specific backup controls:
1043
+
1044
+ **Resource-Specific Controls** (existing):
1045
+ - `backup-recovery-point-encrypted`: Validates individual recovery points are encrypted
1046
+ - `backup-recovery-point-minimum-retention-check`: Checks retention of recovery points
1047
+ - `backup-recovery-point-manual-deletion-disabled`: Ensures manual deletion is disabled
1048
+ - And 9 other resource-specific backup controls
1049
+
1050
+ **Service-Level Controls** (new):
1051
+ - `backup-plan-min-frequency-and-min-retention-check`: Validates backup plan policies
1052
+ - `backup-vault-access-policy-check`: Checks backup vault security
1053
+
1054
+ This hybrid approach provides comprehensive backup coverage at both the service configuration level and individual resource level.
docs/cli-reference.md CHANGED
@@ -1,6 +1,6 @@
1
1
  # CLI Reference
2
2
 
3
- Complete command-line interface reference for the AWS CIS Controls Compliance Assessment Framework - a production-ready enterprise solution with 136 implemented rules (131 CIS Controls + 5 bonus security enhancements).
3
+ Complete command-line interface reference for the AWS CIS Controls Compliance Assessment Framework - a production-ready enterprise solution with 138 implemented rules (133 CIS Controls + 5 bonus security enhancements).
4
4
 
5
5
  ## Table of Contents
6
6
 
@@ -16,7 +16,7 @@ This document provides a comprehensive mapping of CIS Controls to AWS Config rul
16
16
 
17
17
  The AWS CIS Controls Compliance Assessment Framework uses AWS Config rule specifications as the foundation for evaluating compliance. Each CIS Control is mapped to one or more AWS Config rules that assess specific AWS resources and configurations.
18
18
 
19
- **Production Status**: This framework has achieved 100% coverage of all CIS Controls requirements with 136 implemented rules (131 CIS Controls + 5 bonus security enhancements).
19
+ **Production Status**: This framework has achieved 100% coverage of all CIS Controls requirements with 138 implemented rules (133 CIS Controls + 5 bonus security enhancements).
20
20
 
21
21
  ### Mapping Methodology
22
22
 
@@ -27,11 +27,11 @@ The AWS CIS Controls Compliance Assessment Framework uses AWS Config rule specif
27
27
 
28
28
  ### Implementation Groups Hierarchy
29
29
 
30
- - **IG1**: 93 Config rules covering essential cyber hygiene
31
- - **IG2**: +37 Config rules for enhanced security (includes all IG1 rules)
30
+ - **IG1**: 96 Config rules covering essential cyber hygiene
31
+ - **IG2**: +40 Config rules for enhanced security (includes all IG1 rules)
32
32
  - **IG3**: +1 Config rule for advanced security (includes all IG1+IG2 rules)
33
33
  - **Bonus**: +5 additional security rules beyond CIS requirements
34
- - **Total**: 136 Config rules implemented (131 CIS + 5 bonus)
34
+ - **Total**: 142 Config rules implemented (137 CIS + 5 bonus)
35
35
 
36
36
  ## IG1 - Essential Cyber Hygiene
37
37
 
@@ -106,6 +106,47 @@ The AWS CIS Controls Compliance Assessment Framework uses AWS Config rule specif
106
106
  - Checks for proper resource utilization and maintenance
107
107
  - Ensures automatic security updates and rotation policies
108
108
 
109
+ ### Control 11.1: Establish and Maintain a Data Recovery Process
110
+
111
+ **Purpose**: Establish and maintain a data recovery process for enterprise data.
112
+
113
+ | Config Rule | Resource Types | Description |
114
+ |-------------|----------------|-------------|
115
+ | `backup-recovery-point-encrypted` | AWS::Backup::RecoveryPoint | Ensures backup recovery points are encrypted |
116
+ | `backup-recovery-point-minimum-retention-check` | AWS::Backup::RecoveryPoint | Validates recovery point retention periods |
117
+ | `backup-recovery-point-manual-deletion-disabled` | AWS::Backup::RecoveryPoint | Ensures manual deletion is disabled for recovery points |
118
+ | `backup-plan-min-frequency-and-min-retention-check` | AWS::Backup::BackupPlan | Validates backup plan frequency and retention policies |
119
+ | `backup-vault-access-policy-check` | AWS::Backup::BackupVault | Checks backup vault access policies for security |
120
+ | `backup-selection-resource-coverage-check` | AWS::Backup::BackupPlan | Ensures backup plans cover critical resources |
121
+ | `db-instance-backup-enabled` | AWS::RDS::DBInstance | Ensures RDS instances have automated backups enabled |
122
+ | `dynamodb-pitr-enabled` | AWS::DynamoDB::Table | Ensures DynamoDB tables have point-in-time recovery |
123
+ | `elasticache-redis-cluster-automatic-backup-check` | AWS::ElastiCache::CacheCluster | Validates ElastiCache Redis backup configuration |
124
+ | `redshift-backup-enabled` | AWS::Redshift::Cluster | Ensures Redshift clusters have automated backups |
125
+ | `aurora-resources-protected-by-backup-plan` | AWS::RDS::DBCluster | Ensures Aurora clusters are protected by backup plans |
126
+ | `rds-resources-protected-by-backup-plan` | AWS::RDS::DBInstance | Ensures RDS instances are protected by backup plans |
127
+ | `dynamodb-resources-protected-by-backup-plan` | AWS::DynamoDB::Table | Ensures DynamoDB tables are protected by backup plans |
128
+ | `ebs-resources-protected-by-backup-plan` | AWS::EC2::Volume | Ensures EBS volumes are protected by backup plans |
129
+ | `efs-resources-protected-by-backup-plan` | AWS::EFS::FileSystem | Ensures EFS file systems are protected by backup plans |
130
+
131
+ **Assessment Logic**:
132
+ - Validates backup plan configuration and policies
133
+ - Checks backup vault security and access controls
134
+ - Ensures recovery points meet retention requirements
135
+ - Validates encryption of backup data
136
+ - Confirms resources are protected by backup plans
137
+ - Checks automated backup configuration across services
138
+ - Validates backup selections cover critical resources
139
+
140
+ **Service-Level Controls (IG1)**:
141
+ - `backup-plan-min-frequency-and-min-retention-check`: Evaluates backup plans to ensure they have rules with minimum frequency and retention
142
+ - `backup-vault-access-policy-check`: Validates backup vault access policies don't allow overly permissive access (wildcard principals or actions)
143
+ - `backup-selection-resource-coverage-check`: Ensures backup plans have selections that target resources (not empty plans)
144
+
145
+ **Service-Level Controls (IG2)**:
146
+ - `backup-vault-lock-check`: Verifies vault lock is enabled for ransomware protection (immutable backups)
147
+ - `backup-report-plan-exists-check`: Validates backup compliance reporting is configured
148
+ - `backup-restore-testing-plan-exists-check`: Ensures backup recoverability is validated through restore testing
149
+
109
150
  ### Control 5.2: Use Unique Passwords
110
151
 
111
152
  **Purpose**: Use unique passwords for all enterprise assets.
@@ -234,7 +275,7 @@ The AWS CIS Controls Compliance Assessment Framework uses AWS Config rule specif
234
275
 
235
276
  ## Bonus Security Rules
236
277
 
237
- Beyond the required 131 CIS Controls rules, the framework includes 5 additional security enhancements:
278
+ Beyond the required 133 CIS Controls rules, the framework includes 5 additional security enhancements:
238
279
 
239
280
  ### Enhanced Logging Security
240
281
  | Config Rule | Resource Types | Description |