Feature: Backup api (#7231)

This commit is contained in:
archinksagar 2024-01-26 16:49:48 -05:00 committed by GitHub
parent 404c1ea9e3
commit 6c7dff6af6
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
29 changed files with 1019 additions and 151 deletions

View File

@ -364,7 +364,7 @@
## appsync
<details>
<summary>24% implemented</summary>
<summary>25% implemented</summary>
- [ ] associate_api
- [ ] associate_merged_graphql_api
@ -394,7 +394,6 @@
- [ ] get_api_association
- [ ] get_api_cache
- [ ] get_data_source
- [ ] get_data_source_introspection
- [ ] get_domain_name
- [ ] get_function
- [X] get_graphql_api
@ -414,7 +413,6 @@
- [X] list_tags_for_resource
- [ ] list_types
- [ ] list_types_by_association
- [ ] start_data_source_introspection
- [X] start_schema_creation
- [ ] start_schema_merge
- [X] tag_resource
@ -575,6 +573,89 @@
- [X] update_auto_scaling_group
</details>
## backup
<details>
<summary>11% implemented</summary>
- [ ] cancel_legal_hold
- [X] create_backup_plan
- [ ] create_backup_selection
- [X] create_backup_vault
- [ ] create_framework
- [ ] create_legal_hold
- [ ] create_logically_air_gapped_backup_vault
- [ ] create_report_plan
- [X] delete_backup_plan
- [ ] delete_backup_selection
- [ ] delete_backup_vault
- [ ] delete_backup_vault_access_policy
- [ ] delete_backup_vault_lock_configuration
- [ ] delete_backup_vault_notifications
- [ ] delete_framework
- [ ] delete_recovery_point
- [ ] delete_report_plan
- [ ] describe_backup_job
- [ ] describe_backup_vault
- [ ] describe_copy_job
- [ ] describe_framework
- [ ] describe_global_settings
- [ ] describe_protected_resource
- [ ] describe_recovery_point
- [ ] describe_region_settings
- [ ] describe_report_job
- [ ] describe_report_plan
- [ ] describe_restore_job
- [ ] disassociate_recovery_point
- [ ] disassociate_recovery_point_from_parent
- [ ] export_backup_plan_template
- [X] get_backup_plan
- [ ] get_backup_plan_from_json
- [ ] get_backup_plan_from_template
- [ ] get_backup_selection
- [ ] get_backup_vault_access_policy
- [ ] get_backup_vault_notifications
- [ ] get_legal_hold
- [ ] get_recovery_point_restore_metadata
- [ ] get_supported_resource_types
- [ ] list_backup_job_summaries
- [ ] list_backup_jobs
- [ ] list_backup_plan_templates
- [ ] list_backup_plan_versions
- [X] list_backup_plans
- [ ] list_backup_selections
- [X] list_backup_vaults
- [ ] list_copy_job_summaries
- [ ] list_copy_jobs
- [ ] list_frameworks
- [ ] list_legal_holds
- [ ] list_protected_resources
- [ ] list_protected_resources_by_backup_vault
- [ ] list_recovery_points_by_backup_vault
- [ ] list_recovery_points_by_legal_hold
- [ ] list_recovery_points_by_resource
- [ ] list_report_jobs
- [ ] list_report_plans
- [ ] list_restore_job_summaries
- [ ] list_restore_jobs
- [X] list_tags
- [ ] put_backup_vault_access_policy
- [ ] put_backup_vault_lock_configuration
- [ ] put_backup_vault_notifications
- [ ] start_backup_job
- [ ] start_copy_job
- [ ] start_report_job
- [ ] start_restore_job
- [ ] stop_backup_job
- [X] tag_resource
- [X] untag_resource
- [ ] update_backup_plan
- [ ] update_framework
- [ ] update_global_settings
- [ ] update_recovery_point_lifecycle
- [ ] update_region_settings
- [ ] update_report_plan
</details>
## batch
<details>
<summary>100% implemented</summary>
@ -1101,7 +1182,6 @@
- [ ] update_pull_request_status
- [ ] update_pull_request_title
- [ ] update_repository_description
- [ ] update_repository_encryption_key
- [ ] update_repository_name
</details>
@ -2653,7 +2733,7 @@
## efs
<details>
<summary>54% implemented</summary>
<summary>56% implemented</summary>
- [X] create_access_point
- [X] create_file_system
@ -2685,24 +2765,20 @@
- [X] tag_resource
- [X] untag_resource
- [ ] update_file_system
- [ ] update_file_system_protection
</details>
## eks
<details>
<summary>26% implemented</summary>
<summary>33% implemented</summary>
- [ ] associate_access_policy
- [ ] associate_encryption_config
- [ ] associate_identity_provider_config
- [ ] create_access_entry
- [ ] create_addon
- [X] create_cluster
- [ ] create_eks_anywhere_subscription
- [X] create_fargate_profile
- [X] create_nodegroup
- [ ] create_pod_identity_association
- [ ] delete_access_entry
- [ ] delete_addon
- [X] delete_cluster
- [ ] delete_eks_anywhere_subscription
@ -2710,7 +2786,6 @@
- [X] delete_nodegroup
- [ ] delete_pod_identity_association
- [ ] deregister_cluster
- [ ] describe_access_entry
- [ ] describe_addon
- [ ] describe_addon_configuration
- [ ] describe_addon_versions
@ -2718,21 +2793,15 @@
- [ ] describe_eks_anywhere_subscription
- [X] describe_fargate_profile
- [ ] describe_identity_provider_config
- [ ] describe_insight
- [X] describe_nodegroup
- [ ] describe_pod_identity_association
- [ ] describe_update
- [ ] disassociate_access_policy
- [ ] disassociate_identity_provider_config
- [ ] list_access_entries
- [ ] list_access_policies
- [ ] list_addons
- [ ] list_associated_access_policies
- [X] list_clusters
- [ ] list_eks_anywhere_subscriptions
- [X] list_fargate_profiles
- [ ] list_identity_provider_configs
- [ ] list_insights
- [X] list_nodegroups
- [ ] list_pod_identity_associations
- [X] list_tags_for_resource
@ -2740,7 +2809,6 @@
- [ ] register_cluster
- [X] tag_resource
- [X] untag_resource
- [ ] update_access_entry
- [ ] update_addon
- [ ] update_cluster_config
- [ ] update_cluster_version
@ -2752,14 +2820,13 @@
## elasticache
<details>
<summary>8% implemented</summary>
<summary>9% implemented</summary>
- [ ] add_tags_to_resource
- [ ] authorize_cache_security_group_ingress
- [ ] batch_apply_update_action
- [ ] batch_stop_update_action
- [ ] complete_migration
- [ ] copy_serverless_cache_snapshot
- [ ] copy_snapshot
- [X] create_cache_cluster
- [ ] create_cache_parameter_group
@ -2767,8 +2834,6 @@
- [ ] create_cache_subnet_group
- [ ] create_global_replication_group
- [ ] create_replication_group
- [ ] create_serverless_cache
- [ ] create_serverless_cache_snapshot
- [ ] create_snapshot
- [X] create_user
- [ ] create_user_group
@ -2780,8 +2845,6 @@
- [ ] delete_cache_subnet_group
- [ ] delete_global_replication_group
- [ ] delete_replication_group
- [ ] delete_serverless_cache
- [ ] delete_serverless_cache_snapshot
- [ ] delete_snapshot
- [X] delete_user
- [ ] delete_user_group
@ -2797,15 +2860,12 @@
- [ ] describe_replication_groups
- [ ] describe_reserved_cache_nodes
- [ ] describe_reserved_cache_nodes_offerings
- [ ] describe_serverless_cache_snapshots
- [ ] describe_serverless_caches
- [ ] describe_service_updates
- [ ] describe_snapshots
- [ ] describe_update_actions
- [ ] describe_user_groups
- [X] describe_users
- [ ] disassociate_global_replication_group
- [ ] export_serverless_cache_snapshot
- [ ] failover_global_replication_group
- [ ] increase_node_groups_in_global_replication_group
- [ ] increase_replica_count
@ -2817,7 +2877,6 @@
- [ ] modify_global_replication_group
- [ ] modify_replication_group
- [ ] modify_replication_group_shard_configuration
- [ ] modify_serverless_cache
- [ ] modify_user
- [ ] modify_user_group
- [ ] purchase_reserved_cache_nodes_offering
@ -3043,7 +3102,6 @@
- [ ] remove_managed_scaling_policy
- [X] remove_tags
- [X] run_job_flow
- [ ] set_keep_job_flow_alive_when_no_steps
- [X] set_termination_protection
- [X] set_visible_to_all_users
- [ ] start_notebook_execution
@ -3663,7 +3721,7 @@
## guardduty
<details>
<summary>15% implemented</summary>
<summary>16% implemented</summary>
- [ ] accept_administrator_invitation
- [ ] accept_invitation
@ -3703,7 +3761,6 @@
- [ ] get_master_account
- [ ] get_member_detectors
- [ ] get_members
- [ ] get_organization_statistics
- [ ] get_remaining_free_trial_days
- [ ] get_threat_intel_set
- [ ] get_usage_statistics
@ -3980,7 +4037,7 @@
## iot
<details>
<summary>31% implemented</summary>
<summary>32% implemented</summary>
- [ ] accept_certificate_transfer
- [ ] add_thing_to_billing_group
@ -4002,7 +4059,6 @@
- [ ] create_authorizer
- [ ] create_billing_group
- [X] create_certificate_from_csr
- [ ] create_certificate_provider
- [ ] create_custom_metric
- [ ] create_dimension
- [X] create_domain_configuration
@ -4035,7 +4091,6 @@
- [ ] delete_billing_group
- [X] delete_ca_certificate
- [X] delete_certificate
- [ ] delete_certificate_provider
- [ ] delete_custom_metric
- [ ] delete_dimension
- [X] delete_domain_configuration
@ -4073,7 +4128,6 @@
- [ ] describe_billing_group
- [X] describe_ca_certificate
- [X] describe_certificate
- [ ] describe_certificate_provider
- [ ] describe_custom_metric
- [ ] describe_default_authorizer
- [ ] describe_detect_mitigation_actions_task
@ -4133,7 +4187,6 @@
- [ ] list_authorizers
- [ ] list_billing_groups
- [ ] list_ca_certificates
- [ ] list_certificate_providers
- [X] list_certificates
- [X] list_certificates_by_ca
- [ ] list_custom_metrics
@ -4214,7 +4267,6 @@
- [ ] update_billing_group
- [X] update_ca_certificate
- [X] update_certificate
- [ ] update_certificate_provider
- [ ] update_custom_metric
- [ ] update_dimension
- [X] update_domain_configuration
@ -4630,7 +4682,6 @@
- [X] put_resource_policy
- [X] put_retention_policy
- [X] put_subscription_filter
- [ ] start_live_tail
- [X] start_query
- [ ] stop_query
- [X] tag_log_group
@ -4677,7 +4728,7 @@
## mediaconnect
<details>
<summary>35% implemented</summary>
<summary>36% implemented</summary>
- [ ] add_bridge_outputs
- [ ] add_bridge_sources
@ -4694,7 +4745,6 @@
- [ ] deregister_gateway_instance
- [ ] describe_bridge
- [X] describe_flow
- [ ] describe_flow_source_metadata
- [ ] describe_gateway
- [ ] describe_gateway_instance
- [ ] describe_offering
@ -4981,10 +5031,9 @@
## opensearch
<details>
<summary>16% implemented</summary>
<summary>17% implemented</summary>
- [ ] accept_inbound_connection
- [ ] add_data_source
- [X] add_tags
- [ ] associate_package
- [ ] authorize_vpc_endpoint_access
@ -4993,7 +5042,6 @@
- [ ] create_outbound_connection
- [ ] create_package
- [ ] create_vpc_endpoint
- [ ] delete_data_source
- [X] delete_domain
- [ ] delete_inbound_connection
- [ ] delete_outbound_connection
@ -5016,12 +5064,10 @@
- [ ] describe_vpc_endpoints
- [ ] dissociate_package
- [X] get_compatible_versions
- [ ] get_data_source
- [ ] get_domain_maintenance_status
- [ ] get_package_version_history
- [ ] get_upgrade_history
- [ ] get_upgrade_status
- [ ] list_data_sources
- [ ] list_domain_maintenances
- [X] list_domain_names
- [ ] list_domains_for_package
@ -5039,7 +5085,6 @@
- [ ] revoke_vpc_endpoint_access
- [ ] start_domain_maintenance
- [ ] start_service_software_update
- [ ] update_data_source
- [X] update_domain_config
- [ ] update_package
- [ ] update_scheduled_action
@ -5592,7 +5637,6 @@
- [ ] update_analysis
- [ ] update_analysis_permissions
- [ ] update_dashboard
- [ ] update_dashboard_links
- [ ] update_dashboard_permissions
- [ ] update_dashboard_published_version
- [ ] update_data_set
@ -5663,7 +5707,7 @@
## rds
<details>
<summary>35% implemented</summary>
<summary>37% implemented</summary>
- [ ] add_role_to_db_cluster
- [ ] add_role_to_db_instance
@ -5739,7 +5783,6 @@
- [ ] describe_db_proxy_endpoints
- [ ] describe_db_proxy_target_groups
- [ ] describe_db_proxy_targets
- [ ] describe_db_recommendations
- [ ] describe_db_security_groups
- [ ] describe_db_snapshot_attributes
- [ ] describe_db_snapshot_tenant_databases
@ -5762,9 +5805,7 @@
- [ ] describe_source_regions
- [ ] describe_tenant_databases
- [ ] describe_valid_db_instance_modifications
- [ ] disable_http_endpoint
- [ ] download_db_log_file_portion
- [ ] enable_http_endpoint
- [ ] failover_db_cluster
- [ ] failover_global_cluster
- [X] list_tags_for_resource
@ -5781,7 +5822,6 @@
- [ ] modify_db_proxy
- [ ] modify_db_proxy_endpoint
- [ ] modify_db_proxy_target_group
- [ ] modify_db_recommendation
- [ ] modify_db_snapshot
- [ ] modify_db_snapshot_attribute
- [X] modify_db_subnet_group
@ -6323,14 +6363,13 @@
## s3
<details>
<summary>66% implemented</summary>
<summary>68% implemented</summary>
- [X] abort_multipart_upload
- [X] complete_multipart_upload
- [X] copy_object
- [X] create_bucket
- [X] create_multipart_upload
- [ ] create_session
- [X] delete_bucket
- [ ] delete_bucket_analytics_configuration
- [X] delete_bucket_cors
@ -6386,7 +6425,6 @@
- [ ] list_bucket_inventory_configurations
- [ ] list_bucket_metrics_configurations
- [X] list_buckets
- [ ] list_directory_buckets
- [ ] list_multipart_uploads
- [X] list_object_versions
- [X] list_objects
@ -6526,7 +6564,7 @@
## sagemaker
<details>
<summary>19% implemented</summary>
<summary>20% implemented</summary>
- [ ] add_association
- [X] add_tags
@ -6539,7 +6577,6 @@
- [ ] create_artifact
- [ ] create_auto_ml_job
- [ ] create_auto_ml_job_v2
- [ ] create_cluster
- [ ] create_code_repository
- [ ] create_compilation_job
- [ ] create_context
@ -6559,7 +6596,6 @@
- [ ] create_hyper_parameter_tuning_job
- [ ] create_image
- [ ] create_image_version
- [ ] create_inference_component
- [ ] create_inference_experiment
- [ ] create_inference_recommendations_job
- [ ] create_labeling_job
@ -6594,9 +6630,7 @@
- [ ] delete_app_image_config
- [ ] delete_artifact
- [ ] delete_association
- [ ] delete_cluster
- [ ] delete_code_repository
- [ ] delete_compilation_job
- [ ] delete_context
- [ ] delete_data_quality_job_definition
- [ ] delete_device_fleet
@ -6613,7 +6647,6 @@
- [ ] delete_human_task_ui
- [ ] delete_image
- [ ] delete_image_version
- [ ] delete_inference_component
- [ ] delete_inference_experiment
- [X] delete_model
- [ ] delete_model_bias_job_definition
@ -6644,8 +6677,6 @@
- [ ] describe_artifact
- [ ] describe_auto_ml_job
- [ ] describe_auto_ml_job_v2
- [ ] describe_cluster
- [ ] describe_cluster_node
- [ ] describe_code_repository
- [ ] describe_compilation_job
- [ ] describe_context
@ -6667,7 +6698,6 @@
- [ ] describe_hyper_parameter_tuning_job
- [ ] describe_image
- [ ] describe_image_version
- [ ] describe_inference_component
- [ ] describe_inference_experiment
- [ ] describe_inference_recommendations_job
- [ ] describe_labeling_job
@ -6717,8 +6747,6 @@
- [ ] list_associations
- [ ] list_auto_ml_jobs
- [ ] list_candidates_for_auto_ml_job
- [ ] list_cluster_nodes
- [ ] list_clusters
- [ ] list_code_repositories
- [ ] list_compilation_jobs
- [ ] list_contexts
@ -6740,7 +6768,6 @@
- [ ] list_hyper_parameter_tuning_jobs
- [ ] list_image_versions
- [ ] list_images
- [ ] list_inference_components
- [ ] list_inference_experiments
- [ ] list_inference_recommendations_job_steps
- [ ] list_inference_recommendations_jobs
@ -6813,7 +6840,6 @@
- [ ] update_action
- [ ] update_app_image_config
- [ ] update_artifact
- [ ] update_cluster
- [ ] update_code_repository
- [ ] update_context
- [ ] update_device_fleet
@ -6827,8 +6853,6 @@
- [ ] update_hub
- [ ] update_image
- [ ] update_image_version
- [ ] update_inference_component
- [ ] update_inference_component_runtime_config
- [ ] update_inference_experiment
- [ ] update_model_card
- [X] update_model_package
@ -7658,7 +7682,7 @@
## transcribe
<details>
<summary>37% implemented</summary>
<summary>41% implemented</summary>
- [ ] create_call_analytics_category
- [ ] create_language_model
@ -7668,7 +7692,6 @@
- [ ] delete_call_analytics_category
- [ ] delete_call_analytics_job
- [ ] delete_language_model
- [ ] delete_medical_scribe_job
- [X] delete_medical_transcription_job
- [X] delete_medical_vocabulary
- [X] delete_transcription_job
@ -7677,7 +7700,6 @@
- [ ] describe_language_model
- [ ] get_call_analytics_category
- [ ] get_call_analytics_job
- [ ] get_medical_scribe_job
- [X] get_medical_transcription_job
- [X] get_medical_vocabulary
- [X] get_transcription_job
@ -7686,7 +7708,6 @@
- [ ] list_call_analytics_categories
- [ ] list_call_analytics_jobs
- [ ] list_language_models
- [ ] list_medical_scribe_jobs
- [X] list_medical_transcription_jobs
- [X] list_medical_vocabularies
- [ ] list_tags_for_resource
@ -7694,7 +7715,6 @@
- [X] list_vocabularies
- [ ] list_vocabulary_filters
- [ ] start_call_analytics_job
- [ ] start_medical_scribe_job
- [X] start_medical_transcription_job
- [X] start_transcription_job
- [ ] tag_resource
@ -7785,14 +7805,10 @@
- arc-zonal-shift
- auditmanager
- autoscaling-plans
- b2bi
- backup
- backup-gateway
- backupstorage
- bcm-data-exports
- bedrock
- bedrock-agent
- bedrock-agent-runtime
- bedrock-runtime
- billingconductor
- braket
@ -7803,7 +7819,6 @@
- chime-sdk-messaging
- chime-sdk-voice
- cleanrooms
- cleanroomsml
- cloud9
- cloudcontrol
- clouddirectory
@ -7915,9 +7930,7 @@
- machinelearning
- macie2
- managedblockchain-query
- marketplace-agreement
- marketplace-catalog
- marketplace-deployment
- marketplace-entitlement
- marketplacecommerceanalytics
- mediaconvert
@ -7935,11 +7948,9 @@
- mobile
- mturk
- mwaa
- neptune-graph
- neptunedata
- network-firewall
- networkmanager
- networkmonitor
- nimble
- oam
- omics
@ -7960,8 +7971,6 @@
- pricing
- privatenetworks
- proton
- qbusiness
- qconnect
- qldb
- qldb-session
- rbin

View File

@ -55,7 +55,6 @@ appsync
- [ ] get_api_association
- [ ] get_api_cache
- [ ] get_data_source
- [ ] get_data_source_introspection
- [ ] get_domain_name
- [ ] get_function
- [X] get_graphql_api
@ -83,7 +82,6 @@ appsync
- [X] list_tags_for_resource
- [ ] list_types
- [ ] list_types_by_association
- [ ] start_data_source_introspection
- [X] start_schema_creation
- [ ] start_schema_merge
- [X] tag_resource

View File

@ -0,0 +1,119 @@
.. _implementedservice_backup:
.. |start-h3| raw:: html
<h3>
.. |end-h3| raw:: html
</h3>
======
backup
======
.. autoclass:: moto.backup.models.BackupBackend
|start-h3| Example usage |end-h3|
.. sourcecode:: python
@mock_backup
def test_backup_behaviour:
boto3.client("backup")
...
|start-h3| Implemented features for this service |end-h3|
- [ ] cancel_legal_hold
- [X] create_backup_plan
- [ ] create_backup_selection
- [X] create_backup_vault
- [ ] create_framework
- [ ] create_legal_hold
- [ ] create_logically_air_gapped_backup_vault
- [ ] create_report_plan
- [X] delete_backup_plan
- [ ] delete_backup_selection
- [ ] delete_backup_vault
- [ ] delete_backup_vault_access_policy
- [ ] delete_backup_vault_lock_configuration
- [ ] delete_backup_vault_notifications
- [ ] delete_framework
- [ ] delete_recovery_point
- [ ] delete_report_plan
- [ ] describe_backup_job
- [ ] describe_backup_vault
- [ ] describe_copy_job
- [ ] describe_framework
- [ ] describe_global_settings
- [ ] describe_protected_resource
- [ ] describe_recovery_point
- [ ] describe_region_settings
- [ ] describe_report_job
- [ ] describe_report_plan
- [ ] describe_restore_job
- [ ] disassociate_recovery_point
- [ ] disassociate_recovery_point_from_parent
- [ ] export_backup_plan_template
- [X] get_backup_plan
- [ ] get_backup_plan_from_json
- [ ] get_backup_plan_from_template
- [ ] get_backup_selection
- [ ] get_backup_vault_access_policy
- [ ] get_backup_vault_notifications
- [ ] get_legal_hold
- [ ] get_recovery_point_restore_metadata
- [ ] get_supported_resource_types
- [ ] list_backup_job_summaries
- [ ] list_backup_jobs
- [ ] list_backup_plan_templates
- [ ] list_backup_plan_versions
- [X] list_backup_plans
Pagination is not yet implemented
- [ ] list_backup_selections
- [X] list_backup_vaults
Pagination is not yet implemented
- [ ] list_copy_job_summaries
- [ ] list_copy_jobs
- [ ] list_frameworks
- [ ] list_legal_holds
- [ ] list_protected_resources
- [ ] list_protected_resources_by_backup_vault
- [ ] list_recovery_points_by_backup_vault
- [ ] list_recovery_points_by_legal_hold
- [ ] list_recovery_points_by_resource
- [ ] list_report_jobs
- [ ] list_report_plans
- [ ] list_restore_job_summaries
- [ ] list_restore_jobs
- [X] list_tags
Pagination is not yet implemented
- [ ] put_backup_vault_access_policy
- [ ] put_backup_vault_lock_configuration
- [ ] put_backup_vault_notifications
- [ ] start_backup_job
- [ ] start_copy_job
- [ ] start_report_job
- [ ] start_restore_job
- [ ] stop_backup_job
- [X] tag_resource
- [X] untag_resource
- [ ] update_backup_plan
- [ ] update_framework
- [ ] update_global_settings
- [ ] update_recovery_point_lifecycle
- [ ] update_region_settings
- [ ] update_report_plan

View File

@ -102,6 +102,5 @@ codecommit
- [ ] update_pull_request_status
- [ ] update_pull_request_title
- [ ] update_repository_description
- [ ] update_repository_encryption_key
- [ ] update_repository_name

View File

@ -98,5 +98,4 @@ efs
- [X] tag_resource
- [X] untag_resource
- [ ] update_file_system
- [ ] update_file_system_protection

View File

@ -25,17 +25,14 @@ eks
|start-h3| Implemented features for this service |end-h3|
- [ ] associate_access_policy
- [ ] associate_encryption_config
- [ ] associate_identity_provider_config
- [ ] create_access_entry
- [ ] create_addon
- [X] create_cluster
- [ ] create_eks_anywhere_subscription
- [X] create_fargate_profile
- [X] create_nodegroup
- [ ] create_pod_identity_association
- [ ] delete_access_entry
- [ ] delete_addon
- [X] delete_cluster
- [ ] delete_eks_anywhere_subscription
@ -43,7 +40,6 @@ eks
- [X] delete_nodegroup
- [ ] delete_pod_identity_association
- [ ] deregister_cluster
- [ ] describe_access_entry
- [ ] describe_addon
- [ ] describe_addon_configuration
- [ ] describe_addon_versions
@ -51,21 +47,15 @@ eks
- [ ] describe_eks_anywhere_subscription
- [X] describe_fargate_profile
- [ ] describe_identity_provider_config
- [ ] describe_insight
- [X] describe_nodegroup
- [ ] describe_pod_identity_association
- [ ] describe_update
- [ ] disassociate_access_policy
- [ ] disassociate_identity_provider_config
- [ ] list_access_entries
- [ ] list_access_policies
- [ ] list_addons
- [ ] list_associated_access_policies
- [X] list_clusters
- [ ] list_eks_anywhere_subscriptions
- [X] list_fargate_profiles
- [ ] list_identity_provider_configs
- [ ] list_insights
- [X] list_nodegroups
- [ ] list_pod_identity_associations
- [X] list_tags_for_resource
@ -85,7 +75,6 @@ eks
This function currently will remove tags on an EKS cluster only. It does not remove tags from a managed node group
- [ ] update_access_entry
- [ ] update_addon
- [ ] update_cluster_config
- [ ] update_cluster_version

View File

@ -32,7 +32,6 @@ elasticache
- [ ] batch_apply_update_action
- [ ] batch_stop_update_action
- [ ] complete_migration
- [ ] copy_serverless_cache_snapshot
- [ ] copy_snapshot
- [X] create_cache_cluster
- [ ] create_cache_parameter_group
@ -40,8 +39,6 @@ elasticache
- [ ] create_cache_subnet_group
- [ ] create_global_replication_group
- [ ] create_replication_group
- [ ] create_serverless_cache
- [ ] create_serverless_cache_snapshot
- [ ] create_snapshot
- [X] create_user
- [ ] create_user_group
@ -53,8 +50,6 @@ elasticache
- [ ] delete_cache_subnet_group
- [ ] delete_global_replication_group
- [ ] delete_replication_group
- [ ] delete_serverless_cache
- [ ] delete_serverless_cache_snapshot
- [ ] delete_snapshot
- [X] delete_user
- [ ] delete_user_group
@ -70,8 +65,6 @@ elasticache
- [ ] describe_replication_groups
- [ ] describe_reserved_cache_nodes
- [ ] describe_reserved_cache_nodes_offerings
- [ ] describe_serverless_cache_snapshots
- [ ] describe_serverless_caches
- [ ] describe_service_updates
- [ ] describe_snapshots
- [ ] describe_update_actions
@ -83,7 +76,6 @@ elasticache
- [ ] disassociate_global_replication_group
- [ ] export_serverless_cache_snapshot
- [ ] failover_global_replication_group
- [ ] increase_node_groups_in_global_replication_group
- [ ] increase_replica_count
@ -95,7 +87,6 @@ elasticache
- [ ] modify_global_replication_group
- [ ] modify_replication_group
- [ ] modify_replication_group_shard_configuration
- [ ] modify_serverless_cache
- [ ] modify_user
- [ ] modify_user_group
- [ ] purchase_reserved_cache_nodes_offering

View File

@ -72,7 +72,6 @@ emr
- [ ] remove_managed_scaling_policy
- [X] remove_tags
- [X] run_job_flow
- [ ] set_keep_job_flow_alive_when_no_steps
- [X] set_termination_protection
- [X] set_visible_to_all_users
- [ ] start_notebook_execution

View File

@ -63,7 +63,6 @@ guardduty
- [ ] get_master_account
- [ ] get_member_detectors
- [ ] get_members
- [ ] get_organization_statistics
- [ ] get_remaining_free_trial_days
- [ ] get_threat_intel_set
- [ ] get_usage_statistics

View File

@ -49,7 +49,6 @@ iot
- [ ] create_authorizer
- [ ] create_billing_group
- [X] create_certificate_from_csr
- [ ] create_certificate_provider
- [ ] create_custom_metric
- [ ] create_dimension
- [X] create_domain_configuration
@ -86,7 +85,6 @@ iot
- [ ] delete_billing_group
- [X] delete_ca_certificate
- [X] delete_certificate
- [ ] delete_certificate_provider
- [ ] delete_custom_metric
- [ ] delete_dimension
- [X] delete_domain_configuration
@ -132,7 +130,6 @@ iot
- [ ] describe_billing_group
- [X] describe_ca_certificate
- [X] describe_certificate
- [ ] describe_certificate_provider
- [ ] describe_custom_metric
- [ ] describe_default_authorizer
- [ ] describe_detect_mitigation_actions_task
@ -196,7 +193,6 @@ iot
- [ ] list_authorizers
- [ ] list_billing_groups
- [ ] list_ca_certificates
- [ ] list_certificate_providers
- [X] list_certificates
Pagination is not yet implemented
@ -325,7 +321,6 @@ iot
- [X] update_certificate
- [ ] update_certificate_provider
- [ ] update_custom_metric
- [ ] update_dimension
- [X] update_domain_configuration

View File

@ -126,7 +126,6 @@ logs
- [X] put_retention_policy
- [X] put_subscription_filter
- [ ] start_live_tail
- [X] start_query
- [ ] stop_query
- [X] tag_log_group

View File

@ -40,7 +40,6 @@ mediaconnect
- [ ] deregister_gateway_instance
- [ ] describe_bridge
- [X] describe_flow
- [ ] describe_flow_source_metadata
- [ ] describe_gateway
- [ ] describe_gateway_instance
- [ ] describe_offering

View File

@ -28,7 +28,6 @@ opensearch
|start-h3| Implemented features for this service |end-h3|
- [ ] accept_inbound_connection
- [ ] add_data_source
- [X] add_tags
- [ ] associate_package
- [ ] authorize_vpc_endpoint_access
@ -37,7 +36,6 @@ opensearch
- [ ] create_outbound_connection
- [ ] create_package
- [ ] create_vpc_endpoint
- [ ] delete_data_source
- [X] delete_domain
- [ ] delete_inbound_connection
- [ ] delete_outbound_connection
@ -60,12 +58,10 @@ opensearch
- [ ] describe_vpc_endpoints
- [ ] dissociate_package
- [X] get_compatible_versions
- [ ] get_data_source
- [ ] get_domain_maintenance_status
- [ ] get_package_version_history
- [ ] get_upgrade_history
- [ ] get_upgrade_status
- [ ] list_data_sources
- [ ] list_domain_maintenances
- [X] list_domain_names
- [ ] list_domains_for_package
@ -83,7 +79,6 @@ opensearch
- [ ] revoke_vpc_endpoint_access
- [ ] start_domain_maintenance
- [ ] start_service_software_update
- [ ] update_data_source
- [X] update_domain_config
- [ ] update_package
- [ ] update_scheduled_action

View File

@ -188,7 +188,6 @@ quicksight
- [ ] update_analysis
- [ ] update_analysis_permissions
- [ ] update_dashboard
- [ ] update_dashboard_links
- [ ] update_dashboard_permissions
- [ ] update_dashboard_published_version
- [ ] update_data_set

View File

@ -99,7 +99,6 @@ rds
- [ ] describe_db_proxy_endpoints
- [ ] describe_db_proxy_target_groups
- [ ] describe_db_proxy_targets
- [ ] describe_db_recommendations
- [ ] describe_db_security_groups
- [ ] describe_db_snapshot_attributes
- [ ] describe_db_snapshot_tenant_databases
@ -126,9 +125,7 @@ rds
- [ ] describe_source_regions
- [ ] describe_tenant_databases
- [ ] describe_valid_db_instance_modifications
- [ ] disable_http_endpoint
- [ ] download_db_log_file_portion
- [ ] enable_http_endpoint
- [ ] failover_db_cluster
- [ ] failover_global_cluster
- [X] list_tags_for_resource
@ -145,7 +142,6 @@ rds
- [ ] modify_db_proxy
- [ ] modify_db_proxy_endpoint
- [ ] modify_db_proxy_target_group
- [ ] modify_db_recommendation
- [ ] modify_db_snapshot
- [ ] modify_db_snapshot_attribute
- [X] modify_db_subnet_group
@ -171,7 +167,7 @@ rds
- [ ] restore_db_cluster_to_point_in_time
- [X] restore_db_instance_from_db_snapshot
- [ ] restore_db_instance_from_s3
- [ ] restore_db_instance_to_point_in_time
- [X] restore_db_instance_to_point_in_time
- [ ] revoke_db_security_group_ingress
- [ ] start_activity_stream
- [X] start_db_cluster

View File

@ -32,7 +32,6 @@ s3
- [X] copy_object
- [X] create_bucket
- [X] create_multipart_upload
- [ ] create_session
- [X] delete_bucket
- [ ] delete_bucket_analytics_configuration
- [X] delete_bucket_cors
@ -92,7 +91,6 @@ s3
- [ ] list_bucket_inventory_configurations
- [ ] list_bucket_metrics_configurations
- [X] list_buckets
- [ ] list_directory_buckets
- [ ] list_multipart_uploads
- [X] list_object_versions
- [X] list_objects

View File

@ -36,7 +36,6 @@ sagemaker
- [ ] create_artifact
- [ ] create_auto_ml_job
- [ ] create_auto_ml_job_v2
- [ ] create_cluster
- [ ] create_code_repository
- [ ] create_compilation_job
- [ ] create_context
@ -56,7 +55,6 @@ sagemaker
- [ ] create_hyper_parameter_tuning_job
- [ ] create_image
- [ ] create_image_version
- [ ] create_inference_component
- [ ] create_inference_experiment
- [ ] create_inference_recommendations_job
- [ ] create_labeling_job
@ -91,9 +89,7 @@ sagemaker
- [ ] delete_app_image_config
- [ ] delete_artifact
- [ ] delete_association
- [ ] delete_cluster
- [ ] delete_code_repository
- [ ] delete_compilation_job
- [ ] delete_context
- [ ] delete_data_quality_job_definition
- [ ] delete_device_fleet
@ -110,7 +106,6 @@ sagemaker
- [ ] delete_human_task_ui
- [ ] delete_image
- [ ] delete_image_version
- [ ] delete_inference_component
- [ ] delete_inference_experiment
- [X] delete_model
- [ ] delete_model_bias_job_definition
@ -141,8 +136,6 @@ sagemaker
- [ ] describe_artifact
- [ ] describe_auto_ml_job
- [ ] describe_auto_ml_job_v2
- [ ] describe_cluster
- [ ] describe_cluster_node
- [ ] describe_code_repository
- [ ] describe_compilation_job
- [ ] describe_context
@ -164,7 +157,6 @@ sagemaker
- [ ] describe_hyper_parameter_tuning_job
- [ ] describe_image
- [ ] describe_image_version
- [ ] describe_inference_component
- [ ] describe_inference_experiment
- [ ] describe_inference_recommendations_job
- [ ] describe_labeling_job
@ -214,8 +206,6 @@ sagemaker
- [ ] list_associations
- [ ] list_auto_ml_jobs
- [ ] list_candidates_for_auto_ml_job
- [ ] list_cluster_nodes
- [ ] list_clusters
- [ ] list_code_repositories
- [ ] list_compilation_jobs
- [ ] list_contexts
@ -237,7 +227,6 @@ sagemaker
- [ ] list_hyper_parameter_tuning_jobs
- [ ] list_image_versions
- [ ] list_images
- [ ] list_inference_components
- [ ] list_inference_experiments
- [ ] list_inference_recommendations_job_steps
- [ ] list_inference_recommendations_jobs
@ -315,7 +304,6 @@ sagemaker
- [ ] update_action
- [ ] update_app_image_config
- [ ] update_artifact
- [ ] update_cluster
- [ ] update_code_repository
- [ ] update_context
- [ ] update_device_fleet
@ -329,8 +317,6 @@ sagemaker
- [ ] update_hub
- [ ] update_image
- [ ] update_image_version
- [ ] update_inference_component
- [ ] update_inference_component_runtime_config
- [ ] update_inference_experiment
- [ ] update_model_card
- [X] update_model_package

View File

@ -33,7 +33,6 @@ transcribe
- [ ] delete_call_analytics_category
- [ ] delete_call_analytics_job
- [ ] delete_language_model
- [ ] delete_medical_scribe_job
- [X] delete_medical_transcription_job
- [X] delete_medical_vocabulary
- [X] delete_transcription_job
@ -42,7 +41,6 @@ transcribe
- [ ] describe_language_model
- [ ] get_call_analytics_category
- [ ] get_call_analytics_job
- [ ] get_medical_scribe_job
- [X] get_medical_transcription_job
- [X] get_medical_vocabulary
- [X] get_transcription_job
@ -51,7 +49,6 @@ transcribe
- [ ] list_call_analytics_categories
- [ ] list_call_analytics_jobs
- [ ] list_language_models
- [ ] list_medical_scribe_jobs
- [X] list_medical_transcription_jobs
- [X] list_medical_vocabularies
- [ ] list_tags_for_resource
@ -59,7 +56,6 @@ transcribe
- [X] list_vocabularies
- [ ] list_vocabulary_filters
- [ ] start_call_analytics_job
- [ ] start_medical_scribe_job
- [X] start_medical_transcription_job
- [X] start_transcription_job
- [ ] tag_resource

View File

@ -235,6 +235,7 @@ XRaySegment = load_xray_segment()
mock_xray = lazy_load(".xray", "mock_xray")
mock_xray_client = lazy_load(".xray", "mock_xray_client")
mock_wafv2 = lazy_load(".wafv2", "mock_wafv2")
mock_backup = lazy_load(".backup", "mock_backup", boto3_name="backup")
class MockAll(ContextDecorator):

View File

@ -1,4 +1,4 @@
# autogenerated by moto/scripts/update_backend_index.py
# autogenerated by /Users/oxh252/workspace/moto_contribution/moto/scripts/update_backend_index.py
import re
backend_url_patterns = [
@ -18,6 +18,7 @@ backend_url_patterns = [
("appsync", re.compile("https?://appsync\\.(.+)\\.amazonaws\\.com")),
("athena", re.compile("https?://athena\\.(.+)\\.amazonaws\\.com")),
("autoscaling", re.compile("https?://autoscaling\\.(.+)\\.amazonaws\\.com")),
("backup", re.compile("https?://backup\\.(.+)\\.amazonaws\\.com")),
("batch", re.compile("https?://batch\\.(.+)\\.amazonaws.com")),
("budgets", re.compile("https?://budgets\\.amazonaws\\.com")),
("ce", re.compile("https?://ce\\.(.+)\\.amazonaws\\.com")),

5
moto/backup/__init__.py Normal file
View File

@ -0,0 +1,5 @@
"""backup module initialization; sets value for base decorator."""
from ..core.models import base_decorator
from .models import backup_backends
mock_backup = base_decorator(backup_backends)

16
moto/backup/exceptions.py Normal file
View File

@ -0,0 +1,16 @@
"""Exceptions raised by the backup service."""
from moto.core.exceptions import JsonRESTError
class BackupClientError(JsonRESTError):
code = 400
class AlreadyExistsException(BackupClientError):
def __init__(self, msg: str):
super().__init__("AlreadyExistsException", f"{msg}")
class ResourceNotFoundException(JsonRESTError):
def __init__(self, msg: str):
super().__init__("ResourceNotFoundException", f"{msg}")

236
moto/backup/models.py Normal file
View File

@ -0,0 +1,236 @@
"""BackupBackend class with methods for supported APIs."""
from copy import deepcopy
from typing import Any, Dict, List, Optional, Tuple
from moto.core import BackendDict, BaseBackend, BaseModel
from moto.core.utils import unix_time
from moto.moto_api._internal import mock_random
from moto.utilities.tagging_service import TaggingService
from .exceptions import AlreadyExistsException, ResourceNotFoundException
class Plan(BaseModel):
def __init__(
self,
backup_plan: Dict[str, Any],
creator_request_id: str,
backend: "BackupBackend",
):
self.backup_plan_id = str(mock_random.uuid4())
self.backup_plan_arn = f"arn:aws:backup:{backend.region_name}:{backend.account_id}:backup-plan:{self.backup_plan_id}"
self.creation_date = unix_time()
ran_str = mock_random.get_random_string(length=48)
self.version_id = ran_str
self.creator_request_id = creator_request_id
self.backup_plan = backup_plan
adv_settings = backup_plan.get("AdvancedBackupSettings")
self.advanced_backup_settings = adv_settings or []
self.deletion_date: Optional[float] = None
# Deletion Date is updated when the backup_plan is deleted
self.last_execution_date = None # start_restore_job not yet supported
rules = backup_plan["Rules"]
for rule in rules:
rule["ScheduleExpression"] = rule.get(
"ScheduleExpression", "cron(0 5 ? * * *)"
) # Default CRON expression in UTC
rule["StartWindowMinutes"] = rule.get(
"StartWindowMinutes", 480
) # Default=480
rule["CompletionWindowMinutes"] = rule.get(
"CompletionWindowMinutes", 10080
) # Default=10080
rule["ScheduleExpressionTimezone"] = rule.get(
"ScheduleExpressionTimezone", "Etc/UTC"
) # set to Etc/UTc by default
rule["RuleId"] = str(mock_random.uuid4())
def to_dict(self) -> Dict[str, Any]:
dct = {
"BackupPlanId": self.backup_plan_id,
"BackupPlanArn": self.backup_plan_arn,
"CreationDate": self.creation_date,
"VersionId": self.version_id,
"AdvancedBackupSettings": self.advanced_backup_settings,
}
return {k: v for k, v in dct.items() if v}
def to_get_dict(self) -> Dict[str, Any]:
dct = self.to_dict()
dct_options = {
"BackupPlan": self.backup_plan,
"CreatorRequestId": self.creator_request_id,
"DeletionDate": self.deletion_date,
"LastExecutionDate": self.last_execution_date,
}
for key, value in dct_options.items():
if value is not None:
dct[key] = value
return dct
def to_list_dict(self) -> Dict[str, Any]:
dct = self.to_get_dict()
dct.pop("BackupPlan")
dct["BackupPlanName"] = self.backup_plan.get("BackupPlanName")
return dct
class Vault(BaseModel):
def __init__(
self,
backup_vault_name: str,
encryption_key_arn: str,
creator_request_id: str,
backend: "BackupBackend",
):
self.backup_vault_name = backup_vault_name
self.backup_vault_arn = f"arn:aws:backup:{backend.region_name}:{backend.account_id}:backup-vault:{backup_vault_name}"
self.creation_date = unix_time()
self.encryption_key_arn = encryption_key_arn
self.creator_request_id = creator_request_id
self.num_of_recovery_points = 0 # start_backup_job not yet supported
self.locked = False # put_backup_vault_lock_configuration
self.min_retention_days = 0 # put_backup_vault_lock_configuration
self.max_retention_days = 0 # put_backup_vault_lock_configuration
self.lock_date = None # put_backup_vault_lock_configuration
def to_dict(self) -> Dict[str, Any]:
dct = {
"BackupVaultName": self.backup_vault_name,
"BackupVaultArn": self.backup_vault_arn,
"CreationDate": self.creation_date,
}
return dct
def to_list_dict(self) -> Dict[str, Any]:
dct = self.to_dict()
dct_options: Dict[str, Any] = dict()
dct_options = {
"EncryptionKeyArn": self.encryption_key_arn,
"CreatorRequestId": self.creator_request_id,
"NumberOfRecoveryPoints": self.num_of_recovery_points,
"Locked": self.locked,
"MinRetentionDays": self.min_retention_days,
"MaxRetentionDays": self.max_retention_days,
"LockDate": self.lock_date,
}
for key, value in dct_options.items():
if value is not None:
dct[key] = value
return dct
class BackupBackend(BaseBackend):
"""Implementation of Backup APIs."""
def __init__(self, region_name: str, account_id: str):
super().__init__(region_name, account_id)
self.vaults: Dict[str, Vault] = dict()
self.plans: Dict[str, Plan] = dict()
self.tagger = TaggingService()
def create_backup_plan(
self,
backup_plan: Dict[str, Any],
backup_plan_tags: Dict[str, str],
creator_request_id: str,
) -> Plan:
if backup_plan["BackupPlanName"] in list(
p.backup_plan["BackupPlanName"] for p in list(self.plans.values())
):
raise AlreadyExistsException(
msg="Backup plan with the same plan document already exists"
)
plan = Plan(
backup_plan=backup_plan,
creator_request_id=creator_request_id,
backend=self,
)
if backup_plan_tags:
self.tag_resource(plan.backup_plan_arn, backup_plan_tags)
self.plans[plan.backup_plan_id] = plan
return plan
def get_backup_plan(self, backup_plan_id: str, version_id: Optional[Any]) -> Plan:
msg = "Failed reading Backup plan with provided version"
if backup_plan_id not in self.plans:
raise ResourceNotFoundException(msg=msg)
plan = self.plans[backup_plan_id]
if version_id:
if plan.version_id == version_id:
return plan
else:
raise ResourceNotFoundException(msg=msg)
return plan
def delete_backup_plan(self, backup_plan_id: str) -> Tuple[str, str, float, str]:
if backup_plan_id not in self.plans:
raise ResourceNotFoundException(
msg="Failed reading Backup plan with provided version"
)
deletion_date = unix_time()
res = self.plans[backup_plan_id]
res.deletion_date = deletion_date
return res.backup_plan_id, res.backup_plan_arn, deletion_date, res.version_id
def list_backup_plans(self, include_deleted: Any) -> List[Plan]:
"""
Pagination is not yet implemented
"""
plans_list = deepcopy(self.plans)
for plan in list(plans_list.values()):
backup_plan_id = plan.backup_plan_id
if plan.deletion_date is not None:
plans_list.pop(backup_plan_id)
if include_deleted:
return list(self.plans.values())
return list(plans_list.values())
def create_backup_vault(
self,
backup_vault_name: str,
backup_vault_tags: Dict[str, str],
encryption_key_arn: str,
creator_request_id: str,
) -> Vault:
if backup_vault_name in self.vaults:
raise AlreadyExistsException(
msg="Backup vault with the same name already exists"
)
vault = Vault(
backup_vault_name=backup_vault_name,
encryption_key_arn=encryption_key_arn,
creator_request_id=creator_request_id,
backend=self,
)
if backup_vault_tags:
self.tag_resource(vault.backup_vault_arn, backup_vault_tags)
self.vaults[backup_vault_name] = vault
return vault
def list_backup_vaults(self) -> List[Vault]:
"""
Pagination is not yet implemented
"""
return list(self.vaults.values())
def list_tags(self, resource_arn: str) -> Dict[str, str]:
"""
Pagination is not yet implemented
"""
return self.tagger.get_tag_dict_for_resource(resource_arn)
def tag_resource(self, resource_arn: str, tags: Dict[str, str]) -> None:
tags_input = TaggingService.convert_dict_to_tags_input(tags or {})
self.tagger.tag_resource(resource_arn, tags_input)
def untag_resource(self, resource_arn: str, tag_key_list: List[str]) -> None:
self.tagger.untag_resource_using_names(resource_arn, tag_key_list)
backup_backends = BackendDict(BackupBackend, "backup")

116
moto/backup/responses.py Normal file
View File

@ -0,0 +1,116 @@
"""Handles incoming backup requests, invokes methods, returns responses."""
import json
from urllib.parse import unquote
from moto.core.responses import BaseResponse
from .models import BackupBackend, backup_backends
class BackupResponse(BaseResponse):
"""Handler for Backup requests and responses."""
def __init__(self) -> None:
super().__init__(service_name="backup")
@property
def backup_backend(self) -> BackupBackend:
"""Return backend instance specific for this region."""
return backup_backends[self.current_account][self.region]
def create_backup_plan(self) -> str:
params = json.loads(self.body)
backup_plan = params.get("BackupPlan")
backup_plan_tags = params.get("BackupPlanTags")
creator_request_id = params.get("CreatorRequestId")
plan = self.backup_backend.create_backup_plan(
backup_plan=backup_plan,
backup_plan_tags=backup_plan_tags,
creator_request_id=creator_request_id,
)
return json.dumps(dict(plan.to_dict()))
def get_backup_plan(self) -> str:
params = self._get_params()
backup_plan_id = self.path.split("/")[-2]
version_id = params.get("versionId")
plan = self.backup_backend.get_backup_plan(
backup_plan_id=backup_plan_id, version_id=version_id
)
return json.dumps(dict(plan.to_get_dict()))
def delete_backup_plan(self) -> str:
backup_plan_id = self.path.split("/")[-1]
(
backup_plan_id,
backup_plan_arn,
deletion_date,
version_id,
) = self.backup_backend.delete_backup_plan(
backup_plan_id=backup_plan_id,
)
return json.dumps(
dict(
BackupPlanId=backup_plan_id,
BackupPlanArn=backup_plan_arn,
DeletionDate=deletion_date,
VersionId=version_id,
)
)
def list_backup_plans(self) -> str:
params = self._get_params()
include_deleted = params.get("includeDeleted")
backup_plans_list = self.backup_backend.list_backup_plans(
include_deleted=include_deleted
)
return json.dumps(
dict(BackupPlansList=[p.to_list_dict() for p in backup_plans_list])
)
def create_backup_vault(self) -> str:
params = json.loads(self.body)
backup_vault_name = self.path.split("/")[-1]
backup_vault_tags = params.get("BackupVaultTags")
encryption_key_arn = params.get("EncryptionKeyArn")
creator_request_id = params.get("CreatorRequestId")
backup_vault = self.backup_backend.create_backup_vault(
backup_vault_name=backup_vault_name,
backup_vault_tags=backup_vault_tags,
encryption_key_arn=encryption_key_arn,
creator_request_id=creator_request_id,
)
return json.dumps(dict(backup_vault.to_dict()))
def list_backup_vaults(self) -> str:
backup_vault_list = self.backup_backend.list_backup_vaults()
return json.dumps(
dict(BackupVaultList=[v.to_list_dict() for v in backup_vault_list])
)
def list_tags(self) -> str:
resource_arn = unquote(self.path.split("/")[-2])
tags = self.backup_backend.list_tags(
resource_arn=resource_arn,
)
return json.dumps(dict(Tags=tags))
def tag_resource(self) -> str:
params = json.loads(self.body)
resource_arn = unquote(self.path.split("/")[-1])
tags = params.get("Tags")
self.backup_backend.tag_resource(
resource_arn=resource_arn,
tags=tags,
)
return "{}"
def untag_resource(self) -> str:
params = json.loads(self.body)
resource_arn = unquote(self.path.split("/")[-1])
tag_key_list = params.get("TagKeyList")
self.backup_backend.untag_resource(
resource_arn=resource_arn,
tag_key_list=tag_key_list,
)
return "{}"

19
moto/backup/urls.py Normal file
View File

@ -0,0 +1,19 @@
"""backup base URL and path."""
from .responses import BackupResponse
url_bases = [
r"https?://backup\.(.+)\.amazonaws\.com",
]
response = BackupResponse()
url_paths = {
"{0}/backup/plans/?$": response.dispatch,
"{0}/backup/plans/(?P<name>.+)/?$": response.dispatch,
"{0}/backup-vaults/$": response.dispatch,
"{0}/backup-vaults/(?P<name>[^/]+)$": response.dispatch,
"{0}/tags/(?P<resource_arn>.+)$": response.dispatch,
"{0}/untag/(?P<resource_arn>.+)$": response.dispatch,
}

View File

@ -2,6 +2,7 @@ from typing import Any, Dict, Iterator, List, Optional, Tuple
from moto.acm.models import AWSCertificateManagerBackend, acm_backends
from moto.awslambda.models import LambdaBackend, lambda_backends
from moto.backup.models import BackupBackend, backup_backends
from moto.core import BackendDict, BaseBackend
from moto.core.exceptions import RESTError
from moto.ec2 import ec2_backends
@ -100,6 +101,10 @@ class ResourceGroupsTaggingAPIBackend(BaseBackend):
def sqs_backend(self) -> SQSBackend:
return sqs_backends[self.account_id][self.region_name]
@property
def backup_backend(self) -> BackupBackend:
return backup_backends[self.account_id][self.region_name]
def _get_resources_generator(
self,
tag_filters: Optional[List[Dict[str, Any]]] = None,
@ -165,6 +170,19 @@ class ResourceGroupsTaggingAPIBackend(BaseBackend):
continue
yield {"ResourceARN": f"{certificate.arn}", "Tags": tags}
# Backup
if not resource_type_filters or "backup" in resource_type_filters:
for vault in self.backup_backend.vaults.values():
tags = self.backup_backend.tagger.list_tags_for_resource(
vault.backup_vault_arn
)["Tags"]
if not tags or not tag_filter(
tags
): # Skip if no tags, or invalid filter
continue
yield {"ResourceARN": f"{vault.backup_vault_arn}", "Tags": tags}
# S3
if not resource_type_filters or "s3" in resource_type_filters:
for bucket in self.s3_backend.buckets.values():

View File

View File

@ -0,0 +1,359 @@
"""Unit tests for backup-supported APIs."""
import boto3
import pytest
from botocore.exceptions import ClientError
from moto import mock_backup
@mock_backup
def test_create_backup_plan():
client = boto3.client("backup", region_name="eu-west-1")
response = client.create_backup_vault(
BackupVaultName="backupvault-foobar",
)
resp = client.create_backup_plan(
BackupPlan={
"BackupPlanName": "backupplan-foobar",
"Rules": [
{
"RuleName": "foobar",
"TargetBackupVaultName": response["BackupVaultName"],
},
],
},
)
assert "BackupPlanId" in resp
assert "BackupPlanArn" in resp
assert "CreationDate" in resp
assert "VersionId" in resp
@mock_backup
def test_create_backup_plan_already_exists():
client = boto3.client("backup", region_name="eu-west-1")
backup_plan_name = "backup_plan_foobar"
rules = [
{
"RuleName": "foobar",
"TargetBackupVaultName": "backup-vault-foobar",
},
]
client.create_backup_plan(
BackupPlan={"BackupPlanName": backup_plan_name, "Rules": rules}
)
with pytest.raises(ClientError) as exc:
client.create_backup_plan(
BackupPlan={"BackupPlanName": backup_plan_name, "Rules": rules}
)
err = exc.value.response["Error"]
assert err["Code"] == "AlreadyExistsException"
@mock_backup
def test_get_backup_plan():
client = boto3.client("backup", region_name="eu-west-1")
response = client.create_backup_vault(
BackupVaultName="backupvault-foobar",
)
plan = client.create_backup_plan(
BackupPlan={
"BackupPlanName": "backupplan-foobar",
"Rules": [
{
"RuleName": "foobar",
"TargetBackupVaultName": response["BackupVaultName"],
},
],
},
)
resp = client.get_backup_plan(
BackupPlanId=plan["BackupPlanId"], VersionId=plan["VersionId"]
)
assert "BackupPlan" in resp
@mock_backup
def test_get_backup_plan_invalid_id():
client = boto3.client("backup", region_name="eu-west-1")
with pytest.raises(ClientError) as exc:
client.get_backup_plan(BackupPlanId="foobar")
err = exc.value.response["Error"]
assert err["Code"] == "ResourceNotFoundException"
@mock_backup
def test_get_backup_plan_invalid_version_id():
client = boto3.client("backup", region_name="eu-west-1")
plan = client.create_backup_plan(
BackupPlan={
"BackupPlanName": "backupplan-foobar",
"Rules": [
{
"RuleName": "foobar",
"TargetBackupVaultName": "Backup-vault-foobar",
},
],
},
)
with pytest.raises(ClientError) as exc:
client.get_backup_plan(BackupPlanId=plan["BackupPlanId"], VersionId="foobar")
err = exc.value.response["Error"]
assert err["Code"] == "ResourceNotFoundException"
@mock_backup
def test_get_backup_plan_with_multiple_rules():
client = boto3.client("backup", region_name="eu-west-1")
plan = client.create_backup_plan(
BackupPlan={
"BackupPlanName": "backupplan-foobar",
"Rules": [
{
"RuleName": "rule1",
"TargetBackupVaultName": "backupvault-foobar",
"ScheduleExpression": "cron(0 1 ? * * *)",
"StartWindowMinutes": 60,
"CompletionWindowMinutes": 120,
},
{
"RuleName": "rule2",
"TargetBackupVaultName": "backupvault-foobar",
},
],
},
)
resp = client.get_backup_plan(BackupPlanId=plan["BackupPlanId"])
for rule in resp["BackupPlan"]["Rules"]:
assert "ScheduleExpression" in rule
assert "StartWindowMinutes" in rule
assert "CompletionWindowMinutes" in rule
assert "RuleId" in rule
@mock_backup
def test_delete_backup_plan():
client = boto3.client("backup", region_name="eu-west-1")
response = client.create_backup_vault(
BackupVaultName="backupvault-foobar",
)
plan = client.create_backup_plan(
BackupPlan={
"BackupPlanName": "backupplan-foobar",
"Rules": [
{
"RuleName": "foobar",
"TargetBackupVaultName": response["BackupVaultName"],
},
],
},
)
resp = client.delete_backup_plan(BackupPlanId=plan["BackupPlanId"])
assert "BackupPlanId" in resp
assert "BackupPlanArn" in resp
assert "DeletionDate" in resp
assert "VersionId" in resp
resp = client.get_backup_plan(
BackupPlanId=plan["BackupPlanId"], VersionId=plan["VersionId"]
)
assert "DeletionDate" in resp
@mock_backup
def test_delete_backup_plan_invalid_id():
client = boto3.client("backup", region_name="eu-west-1")
with pytest.raises(ClientError) as exc:
client.delete_backup_plan(BackupPlanId="foobar")
err = exc.value.response["Error"]
assert err["Code"] == "ResourceNotFoundException"
@mock_backup
def test_list_backup_plans():
client = boto3.client("backup", region_name="eu-west-1")
for i in range(1, 3):
client.create_backup_plan(
BackupPlan={
"BackupPlanName": f"backup-plan-{i}",
"Rules": [
{
"RuleName": "foobar",
"TargetBackupVaultName": "backupvault-foobar",
},
],
},
)
resp = client.list_backup_plans()
backup_plans = resp["BackupPlansList"]
assert backup_plans[0]["BackupPlanName"] == "backup-plan-1"
assert backup_plans[1]["BackupPlanName"] == "backup-plan-2"
assert len(backup_plans) == 2
assert resp["ResponseMetadata"]["HTTPStatusCode"] == 200
@mock_backup
def test_list_backup_plans_without_include_deleted():
client = boto3.client("backup", region_name="eu-west-1")
for i in range(1, 3):
client.create_backup_plan(
BackupPlan={
"BackupPlanName": f"backup-plan-{i}",
"Rules": [
{
"RuleName": "foobar",
"TargetBackupVaultName": "backupvault-foobar",
},
],
},
)
resp = client.list_backup_plans()
client.delete_backup_plan(BackupPlanId=resp["BackupPlansList"][0]["BackupPlanId"])
resp_list = client.list_backup_plans()
backup_plans = resp_list["BackupPlansList"]
assert backup_plans[0]["BackupPlanName"] == "backup-plan-2"
assert len(backup_plans) == 1
@mock_backup
def test_list_backup_plans_with_include_deleted():
client = boto3.client("backup", region_name="eu-west-1")
for i in range(1, 3):
client.create_backup_plan(
BackupPlan={
"BackupPlanName": f"backup-plan-{i}",
"Rules": [
{
"RuleName": "foobar",
"TargetBackupVaultName": "backupvault-foobar",
},
],
},
)
resp = client.list_backup_plans()
client.delete_backup_plan(BackupPlanId=resp["BackupPlansList"][0]["BackupPlanId"])
resp_list = client.list_backup_plans(IncludeDeleted=True)
backup_plans = resp_list["BackupPlansList"]
assert backup_plans[0]["BackupPlanName"] == "backup-plan-1"
assert backup_plans[1]["BackupPlanName"] == "backup-plan-2"
assert len(backup_plans) == 2
@mock_backup
def test_create_backup_vault():
client = boto3.client("backup", region_name="eu-west-1")
resp = client.create_backup_vault(
BackupVaultName="backupvault-foobar",
BackupVaultTags={
"foo": "bar",
},
)
assert "BackupVaultName" in resp
assert "BackupVaultArn" in resp
assert "CreationDate" in resp
@mock_backup
def test_create_backup_vault_already_exists():
client = boto3.client("backup", region_name="eu-west-1")
backup_vault_name = "backup_vault_foobar"
client.create_backup_vault(BackupVaultName=backup_vault_name)
with pytest.raises(ClientError) as exc:
client.create_backup_vault(BackupVaultName=backup_vault_name)
err = exc.value.response["Error"]
assert err["Code"] == "AlreadyExistsException"
@mock_backup
def test_list_backup_vaults():
client = boto3.client("backup", region_name="eu-west-1")
for i in range(1, 3):
client.create_backup_vault(
BackupVaultName=f"backup-vault-{i}",
)
resp = client.list_backup_vaults()
backup_plans = resp["BackupVaultList"]
assert backup_plans[0]["BackupVaultName"] == "backup-vault-1"
assert backup_plans[1]["BackupVaultName"] == "backup-vault-2"
assert resp["ResponseMetadata"]["HTTPStatusCode"] == 200
@mock_backup
def test_list_tags_vault():
client = boto3.client("backup", region_name="eu-west-1")
vault = client.create_backup_vault(
BackupVaultName="backupvault-foobar",
BackupVaultTags={
"key1": "value1",
"key2": "value2",
},
)
resp = client.list_tags(ResourceArn=vault["BackupVaultArn"])
assert resp["Tags"] == {"key1": "value1", "key2": "value2"}
@mock_backup
def test_list_tags_plan():
client = boto3.client("backup", region_name="eu-west-1")
response = client.create_backup_vault(
BackupVaultName="backupvault-foobar",
)
plan = client.create_backup_plan(
BackupPlan={
"BackupPlanName": "backupplan-foobar",
"Rules": [
{
"RuleName": "foobar",
"TargetBackupVaultName": response["BackupVaultName"],
},
],
},
BackupPlanTags={
"key1": "value1",
"key2": "value2",
},
)
resp = client.list_tags(ResourceArn=plan["BackupPlanArn"])
assert resp["Tags"] == {"key1": "value1", "key2": "value2"}
@mock_backup
def test_tag_resource():
client = boto3.client("backup", region_name="eu-west-1")
vault = client.create_backup_vault(
BackupVaultName="backupvault-foobar",
BackupVaultTags={
"key1": "value1",
},
)
resource_arn = vault["BackupVaultArn"]
client.tag_resource(
ResourceArn=resource_arn, Tags={"key2": "value2", "key3": "value3"}
)
resp = client.list_tags(ResourceArn=resource_arn)
assert resp["Tags"] == {"key1": "value1", "key2": "value2", "key3": "value3"}
@mock_backup
def test_untag_resource():
client = boto3.client("backup", region_name="eu-west-1")
vault = client.create_backup_vault(
BackupVaultName="backupvault-foobar",
BackupVaultTags={
"key1": "value1",
},
)
resource_arn = vault["BackupVaultArn"]
client.tag_resource(
ResourceArn=resource_arn, Tags={"key2": "value2", "key3": "value3"}
)
resp = client.untag_resource(ResourceArn=resource_arn, TagKeyList=["key2"])
resp = client.list_tags(ResourceArn=resource_arn)
assert resp["Tags"] == {"key1": "value1", "key3": "value3"}

View File

@ -5,6 +5,7 @@ from botocore.client import ClientError
from moto import (
mock_acm,
mock_backup,
mock_cloudformation,
mock_ec2,
mock_ecs,
@ -117,6 +118,37 @@ def test_get_resources_acm():
)
@mock_backup
@mock_resourcegroupstaggingapi
def test_get_resources_backup():
backup = boto3.client("backup", region_name="eu-central-1")
# Create two tagged Backup Vaults
for i in range(1, 3):
i_str = str(i)
backup.create_backup_vault(
BackupVaultName="backup-vault-tag-" + i_str,
BackupVaultTags={
"Test": i_str,
},
)
rtapi = boto3.client("resourcegroupstaggingapi", region_name="eu-central-1")
# Basic test
resp = rtapi.get_resources(ResourceTypeFilters=["backup"])
assert len(resp["ResourceTagMappingList"]) == 2
# Test tag filtering
resp = rtapi.get_resources(
ResourceTypeFilters=["backup"],
TagFilters=[{"Key": "Test", "Values": ["1"]}],
)
assert len(resp["ResourceTagMappingList"]) == 1
assert {"Key": "Test", "Value": "1"} in resp["ResourceTagMappingList"][0]["Tags"]
@mock_ecs
@mock_ec2
@mock_resourcegroupstaggingapi