brightbox-cli 3.3.0 → 4.1.0
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.
- checksums.yaml +4 -4
- data/.gitattributes +1 -0
- data/.github/workflows/ruby.yml +1 -1
- data/.gitignore +1 -1
- data/.rubocop.yml +70 -0
- data/CHANGELOG.md +60 -0
- data/Gemfile.lock +74 -45
- data/Jenkinsfile +12 -32
- data/README +23 -32
- data/README.rdoc +1 -1
- data/brightbox-cli.gemspec +21 -34
- data/lib/brightbox-cli/accounts.rb +9 -11
- data/lib/brightbox-cli/api.rb +38 -36
- data/lib/brightbox-cli/cloud_ips.rb +8 -8
- data/lib/brightbox-cli/collaborating_account.rb +5 -5
- data/lib/brightbox-cli/collaboration.rb +1 -1
- data/lib/brightbox-cli/commands/accounts/{accept-invite.rb → accept_invite.rb} +2 -6
- data/lib/brightbox-cli/commands/accounts/default.rb +1 -2
- data/lib/brightbox-cli/commands/accounts/list.rb +6 -8
- data/lib/brightbox-cli/commands/accounts/remove.rb +2 -6
- data/lib/brightbox-cli/commands/accounts/{reset-ftp-password.rb → reset_ftp_password.rb} +6 -9
- data/lib/brightbox-cli/commands/accounts/show.rb +10 -13
- data/lib/brightbox-cli/commands/cloudips/create.rb +2 -5
- data/lib/brightbox-cli/commands/cloudips/destroy.rb +10 -14
- data/lib/brightbox-cli/commands/cloudips/list.rb +0 -2
- data/lib/brightbox-cli/commands/cloudips/map.rb +10 -13
- data/lib/brightbox-cli/commands/cloudips/show.rb +11 -14
- data/lib/brightbox-cli/commands/cloudips/unmap.rb +2 -4
- data/lib/brightbox-cli/commands/cloudips/update.rb +2 -4
- data/lib/brightbox-cli/commands/collaborations.rb +2 -3
- data/lib/brightbox-cli/commands/config/{client-add.rb → client_add.rb} +0 -3
- data/lib/brightbox-cli/commands/config/client_default.rb +18 -0
- data/lib/brightbox-cli/commands/config/{client-list.rb → client_list.rb} +1 -4
- data/lib/brightbox-cli/commands/config/{client-remove.rb → client_remove.rb} +0 -3
- data/lib/brightbox-cli/commands/config/{user-add.rb → user_add.rb} +1 -4
- data/lib/brightbox-cli/commands/firewall/{policies-apply.rb → policies_apply.rb} +2 -2
- data/lib/brightbox-cli/commands/firewall/{policies-create.rb → policies_create.rb} +2 -4
- data/lib/brightbox-cli/commands/firewall/{policies-destroy.rb → policies_destroy.rb} +0 -3
- data/lib/brightbox-cli/commands/firewall/{policies-list.rb → policies_list.rb} +0 -2
- data/lib/brightbox-cli/commands/firewall/{policies-remove.rb → policies_remove.rb} +2 -2
- data/lib/brightbox-cli/commands/firewall/{policies-show.rb → policies_show.rb} +6 -8
- data/lib/brightbox-cli/commands/firewall/{policies-update.rb → policies_update.rb} +2 -4
- data/lib/brightbox-cli/commands/firewall/{rules-create.rb → rules_create.rb} +6 -8
- data/lib/brightbox-cli/commands/firewall/{rules-destroy.rb → rules_destroy.rb} +0 -2
- data/lib/brightbox-cli/commands/firewall/{rules-list.rb → rules_list.rb} +0 -2
- data/lib/brightbox-cli/commands/firewall/{rules-show.rb → rules_show.rb} +7 -9
- data/lib/brightbox-cli/commands/firewall/{rules-update.rb → rules_update.rb} +7 -8
- data/lib/brightbox-cli/commands/groups/{add-server.rb → add_server.rb} +0 -2
- data/lib/brightbox-cli/commands/groups/create.rb +2 -3
- data/lib/brightbox-cli/commands/groups/destroy.rb +0 -2
- data/lib/brightbox-cli/commands/groups/list.rb +0 -1
- data/lib/brightbox-cli/commands/groups/move_servers.rb +2 -3
- data/lib/brightbox-cli/commands/groups/{remove-servers.rb → remove_servers.rb} +2 -4
- data/lib/brightbox-cli/commands/groups/show.rb +0 -2
- data/lib/brightbox-cli/commands/groups/update.rb +2 -3
- data/lib/brightbox-cli/commands/images/destroy.rb +0 -4
- data/lib/brightbox-cli/commands/images/list.rb +3 -5
- data/lib/brightbox-cli/commands/images/register.rb +9 -17
- data/lib/brightbox-cli/commands/images/show.rb +19 -20
- data/lib/brightbox-cli/commands/images/update.rb +12 -8
- data/lib/brightbox-cli/commands/lbs/{add-nodes.rb → add_nodes.rb} +0 -3
- data/lib/brightbox-cli/commands/lbs/create.rb +5 -7
- data/lib/brightbox-cli/commands/lbs/destroy.rb +0 -3
- data/lib/brightbox-cli/commands/lbs/list.rb +0 -1
- data/lib/brightbox-cli/commands/lbs/{remove-nodes.rb → remove_nodes.rb} +0 -3
- data/lib/brightbox-cli/commands/lbs/show.rb +20 -22
- data/lib/brightbox-cli/commands/lbs/update.rb +6 -9
- data/lib/brightbox-cli/commands/login.rb +13 -12
- data/lib/brightbox-cli/commands/servers/{activate-console.rb → activate_console.rb} +2 -5
- data/lib/brightbox-cli/commands/servers/create.rb +32 -26
- data/lib/brightbox-cli/commands/servers/destroy.rb +0 -3
- data/lib/brightbox-cli/commands/servers/list.rb +4 -5
- data/lib/brightbox-cli/commands/servers/show.rb +0 -2
- data/lib/brightbox-cli/commands/servers/shutdown.rb +0 -3
- data/lib/brightbox-cli/commands/servers/snapshot.rb +0 -4
- data/lib/brightbox-cli/commands/servers/start.rb +0 -4
- data/lib/brightbox-cli/commands/servers/stop.rb +0 -3
- data/lib/brightbox-cli/commands/servers/update.rb +5 -5
- data/lib/brightbox-cli/commands/sql/instances_create.rb +3 -6
- data/lib/brightbox-cli/commands/sql/instances_destroy.rb +0 -2
- data/lib/brightbox-cli/commands/sql/instances_list.rb +7 -9
- data/lib/brightbox-cli/commands/sql/instances_reset_password.rb +0 -1
- data/lib/brightbox-cli/commands/sql/instances_show.rb +0 -3
- data/lib/brightbox-cli/commands/sql/instances_snapshot.rb +0 -3
- data/lib/brightbox-cli/commands/sql/instances_update.rb +1 -3
- data/lib/brightbox-cli/commands/sql/snapshots_destroy.rb +0 -3
- data/lib/brightbox-cli/commands/sql/snapshots_list.rb +7 -9
- data/lib/brightbox-cli/commands/sql/snapshots_show.rb +12 -15
- data/lib/brightbox-cli/commands/sql/snapshots_update.rb +1 -3
- data/lib/brightbox-cli/commands/sql/types.rb +8 -15
- data/lib/brightbox-cli/commands/token.rb +0 -1
- data/lib/brightbox-cli/commands/types.rb +8 -14
- data/lib/brightbox-cli/commands/{user-collaborations.rb → user_collaborations.rb} +7 -8
- data/lib/brightbox-cli/commands/users/list.rb +0 -2
- data/lib/brightbox-cli/commands/users/show.rb +1 -3
- data/lib/brightbox-cli/commands/users/update.rb +3 -6
- data/lib/brightbox-cli/commands/zones.rb +7 -10
- data/lib/brightbox-cli/config/accounts.rb +18 -26
- data/lib/brightbox-cli/config/api_client.rb +12 -16
- data/lib/brightbox-cli/config/authentication_tokens.rb +39 -42
- data/lib/brightbox-cli/config/cache.rb +1 -0
- data/lib/brightbox-cli/config/clients.rb +8 -8
- data/lib/brightbox-cli/config/gpg_encrypted_passwords.rb +6 -8
- data/lib/brightbox-cli/config/password_helper.rb +33 -8
- data/lib/brightbox-cli/config/sections.rb +45 -29
- data/lib/brightbox-cli/config/two_factor_auth.rb +12 -14
- data/lib/brightbox-cli/config/two_factor_helper.rb +5 -7
- data/lib/brightbox-cli/config/user_application.rb +18 -18
- data/lib/brightbox-cli/config.rb +26 -23
- data/lib/brightbox-cli/connection_manager.rb +4 -2
- data/lib/brightbox-cli/database_server.rb +28 -29
- data/lib/brightbox-cli/database_snapshot.rb +1 -1
- data/lib/brightbox-cli/database_type.rb +6 -6
- data/lib/brightbox-cli/detailed_server.rb +43 -43
- data/lib/brightbox-cli/detailed_server_group.rb +1 -1
- data/lib/brightbox-cli/error_parser.rb +9 -9
- data/lib/brightbox-cli/firewall_policy.rb +2 -1
- data/lib/brightbox-cli/firewall_rule.rb +3 -3
- data/lib/brightbox-cli/firewall_rules.rb +3 -3
- data/lib/brightbox-cli/gli_global_hooks.rb +25 -27
- data/lib/brightbox-cli/images.rb +14 -12
- data/lib/brightbox-cli/load_balancers.rb +3 -6
- data/lib/brightbox-cli/logging.rb +14 -14
- data/lib/brightbox-cli/nilable_hash.rb +1 -1
- data/lib/brightbox-cli/ruby_core_ext.rb +3 -3
- data/lib/brightbox-cli/server_groups.rb +2 -2
- data/lib/brightbox-cli/servers.rb +6 -6
- data/lib/brightbox-cli/tables.rb +13 -15
- data/lib/brightbox-cli/types.rb +6 -6
- data/lib/brightbox-cli/user_collaboration.rb +5 -7
- data/lib/brightbox-cli/users.rb +1 -1
- data/lib/brightbox-cli/version.rb +1 -1
- data/lib/brightbox-cli/zones.rb +1 -1
- data/lib/brightbox_cli.rb +33 -33
- data/locales/en.yml +2 -0
- data/spec/brightbox_spec.rb +0 -1
- data/spec/cassettes/Brightbox_Account/_all/when_connected_using_an_application/returns_a_collection_of_Accounts.yml +5 -5
- data/spec/cassettes/Brightbox_Account/_all/when_connected_using_an_application/returns_resources_on_the_same_connection.yml +2 -2
- data/spec/cassettes/Brightbox_Account/_all/when_connected_using_an_client/returns_a_collection_of_Accounts.yml +4 -4
- data/spec/cassettes/Brightbox_Account/_all/when_connected_using_an_client/returns_resources_on_the_same_connection.yml +2 -2
- data/spec/cassettes/Brightbox_BBConfig/_add_section/when_config_exists_and_overwrite_duplicates_is_false/does_not_update_the_config_file.yml +12 -12
- data/spec/cassettes/Brightbox_BBConfig/_add_section/when_config_exists_and_overwrite_duplicates_is_true/does_not_update_the_config_file.yml +12 -12
- data/spec/cassettes/Brightbox_BBConfig/_add_section/when_first_and_only_client/saves_changes_to_the_config_file.yml +2 -2
- data/spec/cassettes/Brightbox_BBConfig/_add_section/when_first_and_only_client/saves_the_default_account.yml +2 -2
- data/spec/cassettes/Brightbox_BBConfig/_add_section/when_first_and_only_client/saves_the_new_client_as_the_default.yml +2 -2
- data/spec/cassettes/Brightbox_BBConfig/_find_or_set_default_account/when_client_is_not_authenticated/does_not_raise_an_error.yml +8 -8
- data/spec/cassettes/Brightbox_BBConfig/_find_or_set_default_account/when_client_may_access_one_account/updates_the_setting.yml +8 -8
- data/spec/cassettes/Brightbox_BBConfig/_renew_tokens/when_config_in_use_is_not_the_default/uses_correct_credentials.yml +1 -1
- data/spec/cassettes/Brightbox_BBConfig/_renew_tokens/when_using_a_user_app_with_a_cached_refresh_token/caches_the_new_tokens.yml +1 -1
- data/spec/cassettes/Brightbox_BBConfig/_renew_tokens/when_using_a_user_app_with_an_expired_refresh_token/caches_the_new_tokens.yml +2 -2
- data/spec/cassettes/Brightbox_BBConfig/_renew_tokens/when_using_a_user_app_with_no_tokens/caches_the_new_tokens.yml +1 -1
- data/spec/cassettes/Brightbox_BBConfig/_renew_tokens/when_using_a_user_app_with_no_tokens/prompts_user_to_retry_command.yml +1 -1
- data/spec/cassettes/Brightbox_BBConfig/_renew_tokens/when_using_an_API_client_with_no_tokens/caches_a_new_access_token.yml +1 -1
- data/spec/cassettes/Brightbox_BBConfig_add_login/when_altering_a_custom_option/does_not_alter_the_configuration.yml +6 -6
- data/spec/cassettes/Brightbox_BBConfig_add_login/when_altering_a_custom_option/updates_access_token.yml +6 -6
- data/spec/cassettes/Brightbox_BBConfig_add_login/when_altering_a_custom_option/updates_refresh_token.yml +6 -6
- data/spec/cassettes/Brightbox_BBConfig_add_login/when_configured_with_custom_options/does_not_alter_the_configuration.yml +6 -6
- data/spec/cassettes/Brightbox_BBConfig_add_login/when_configured_with_custom_options/updates_access_token.yml +6 -6
- data/spec/cassettes/Brightbox_BBConfig_add_login/when_configured_with_custom_options/updates_refresh_token.yml +6 -6
- data/spec/cassettes/Brightbox_BBConfig_add_login/when_logged_in_previously/does_not_alter_the_configuration.yml +9 -9
- data/spec/cassettes/Brightbox_BBConfig_add_login/when_logged_in_previously/updates_access_token.yml +9 -9
- data/spec/cassettes/Brightbox_BBConfig_add_login/when_logged_in_previously/updates_refresh_token.yml +9 -9
- data/spec/cassettes/Brightbox_BBConfig_add_login/when_no_config_exists/creates_the_configuration.yml +6 -6
- data/spec/cassettes/Brightbox_BBConfig_add_login/when_no_config_exists/refreshed_tokens.yml +6 -6
- data/spec/cassettes/Brightbox_BBConfig_add_login/when_using_an_email_and_suffix/creates_the_configuration.yml +6 -6
- data/spec/cassettes/Brightbox_BBConfig_add_login/when_using_an_email_and_suffix/refreshed_tokens.yml +6 -6
- data/spec/cassettes/Brightbox_CloudIP/_find_all_/when_a_Cloud_IP_exists/returns_a_suitable.yml +15 -15
- data/spec/cassettes/Brightbox_FirewallPolicy/_apply_to/should_apply_firewall_policy.yml +14 -14
- data/spec/cassettes/Brightbox_FirewallPolicy/_create/should_create_firewall_policy.yml +14 -14
- data/spec/cassettes/Brightbox_FirewallPolicy/_destroy/should_destroy_firewall_policy.yml +16 -16
- data/spec/cassettes/Brightbox_FirewallPolicy/_find_all_/when_a_policy_exists/should_list_firewall_policy.yml +13 -13
- data/spec/cassettes/Brightbox_FirewallPolicy/_find_or_call/when_a_policy_exists/should_show_firewall_policy.yml +11 -11
- data/spec/cassettes/Brightbox_FirewallRule/_create/when_policy_exists/creates_the_rule_successfully.yml +14 -14
- data/spec/cassettes/Brightbox_FirewallRule/_destroy/when_rule_exists/destroys_a_rule.yml +12 -12
- data/spec/cassettes/Brightbox_FirewallRule/_find/when_rule_exists/can_display_the_result.yml +14 -14
- data/spec/cassettes/Brightbox_FirewallRule/_from_policy/when_policy_exists_with_a_rule/lists_all_rules.yml +19 -19
- data/spec/cassettes/Brightbox_Server/_destroy/when_server_exists/should_work.yml +12 -12
- data/spec/cassettes/Brightbox_Server/_find_all_/when_a_server_exists/should_print_server_list.yml +15 -15
- data/spec/cassettes/Brightbox_Server/_show/when_server_exists/shows_detailed_attributes_of_a_server.yml +18 -18
- data/spec/cassettes/Brightbox_Server/_shutdown/should_work.yml +18 -18
- data/spec/cassettes/Brightbox_Server/_start/should_work.yml +24 -24
- data/spec/cassettes/Brightbox_Server/_stop/should_work.yml +18 -18
- data/spec/cassettes/Brightbox_Server/_update/when_passing_new_group_membership/should_update_with_group.yml +22 -22
- data/spec/cassettes/Brightbox_ServerGroup/_find_all_/when_a_group_exists/list_server_groups.yml +13 -13
- data/spec/cassettes/Firewall_policies/update/when_the_policy_does_not_exist/prints_error_to_STDERR.yml +3 -3
- data/spec/cassettes/brightbox_accounts/list/_when_access_token_expired_/does_not_report_invalid_token_errors.yml +30 -30
- data/spec/cassettes/brightbox_accounts/list/_when_both_tokens_expired_/does_not_report_invalid_token_errors.yml +9 -9
- data/spec/cassettes/brightbox_accounts/list/_when_invalid_tokens_/does_not_report_invalid_token_errors.yml +9 -9
- data/spec/cassettes/brightbox_accounts/list/_when_no_tokens_/does_not_report_invalid_token_errors.yml +27 -27
- data/spec/cassettes/brightbox_accounts/list/_when_no_tokens_/reports_they_were_updated.yml +7 -7
- data/spec/cassettes/brightbox_accounts/list/_when_no_tokens_and_password_incorrect_/does_not_report_invalid_token_errors.yml +7 -7
- data/spec/cassettes/brightbox_accounts/list/_when_no_tokens_and_password_incorrect_/reports_unable_to_authenticate.yml +6 -6
- data/spec/cassettes/brightbox_accounts/list/does_not_error.yml +3 -3
- data/spec/cassettes/brightbox_cloudips/map/when_destination_is_a_server_ID/passes_the_interface_identifier_to_the_API.yml +12 -12
- data/spec/cassettes/brightbox_cloudips/map/when_destination_is_another_value/passes_the_identifier_to_the_API.yml +7 -7
- data/spec/cassettes/brightbox_config/client_add/when_adding_a_new_client/does_not_error.yml +7 -7
- data/spec/cassettes/brightbox_config/client_add/when_adding_a_new_client/sets_up_the_config.yml +7 -7
- data/spec/cassettes/brightbox_config/client_add/when_new_client_is_first_and_only_client/does_not_change_the_default_client.yml +7 -7
- data/spec/cassettes/brightbox_config/client_add/when_new_client_is_first_and_only_client/does_not_error.yml +7 -7
- data/spec/cassettes/brightbox_config/client_add/when_new_client_is_first_and_only_client/sets_this_as_the_default_client.yml +7 -7
- data/spec/cassettes/brightbox_config/client_add/when_new_client_is_first_and_only_client/sets_up_the_config.yml +7 -7
- data/spec/cassettes/brightbox_config/user_add/when_NO_config_file_on_disk/sets_up_the_config.yml +5 -5
- data/spec/cassettes/brightbox_config/user_add/when_a_default_client_is_already_set/does_not_change_the_default_client.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_application_details_in_config/does_not_error.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_application_details_in_config/sets_up_the_config.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_application_has_access_only_one_active_account/display_an_warning_about_preselected_default.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_application_has_access_only_one_active_account/does_not_error.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_application_has_access_only_one_active_account/selects_the_active_account_for_the_default.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_application_has_access_only_one_active_account/sets_up_the_config.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_application_has_access_to_multiple_accounts/display_an_warning_about_preselected_default.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_application_has_access_to_multiple_accounts/does_not_error.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_application_has_access_to_multiple_accounts/sets_up_the_config.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_new_client_is_first_and_only_client/does_not_error.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_new_client_is_first_and_only_client/does_not_prompt_to_rerun_the_command.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_new_client_is_first_and_only_client/requests_access_tokens.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_new_client_is_first_and_only_client/sets_this_as_the_default_client.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_new_client_is_first_and_only_client/sets_up_the_config.yml +5 -5
- data/spec/cassettes/brightbox_config/user_add/when_passing_in_required_arguments/does_not_error.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_passing_in_required_arguments/does_not_prompt_to_rerun_the_command.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_passing_in_required_arguments/requests_access_tokens.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_passing_in_required_arguments/sets_up_the_config.yml +3 -3
- data/spec/cassettes/brightbox_config/user_add/when_passing_in_required_arguments_and_api_url/does_not_error.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_passing_in_required_arguments_and_api_url/requests_access_tokens.yml +2 -2
- data/spec/cassettes/brightbox_config/user_add/when_passing_in_required_arguments_and_api_url/sets_up_the_config.yml +2 -2
- data/spec/cassettes/brightbox_login/when_alternative_client_credentials_are_given/does_not_error.yml +6 -6
- data/spec/cassettes/brightbox_login/when_alternative_client_credentials_are_given/does_not_prompt_to_rerun_the_command.yml +6 -6
- data/spec/cassettes/brightbox_login/when_alternative_client_credentials_are_given/prompts_for_the_password.yml +6 -6
- data/spec/cassettes/brightbox_login/when_alternative_client_credentials_are_given/requests_access_tokens.yml +6 -6
- data/spec/cassettes/brightbox_login/when_alternative_client_credentials_are_given/sets_up_the_config.yml +6 -6
- data/spec/cassettes/brightbox_login/when_custom_api/auth_URLs_are_given/does_not_error.yml +6 -6
- data/spec/cassettes/brightbox_login/when_custom_api/auth_URLs_are_given/does_not_prompt_to_rerun_the_command.yml +6 -6
- data/spec/cassettes/brightbox_login/when_custom_api/auth_URLs_are_given/prompts_for_the_password.yml +6 -6
- data/spec/cassettes/brightbox_login/when_custom_api/auth_URLs_are_given/requests_access_tokens.yml +6 -6
- data/spec/cassettes/brightbox_login/when_custom_api/auth_URLs_are_given/sets_up_the_config.yml +6 -6
- data/spec/cassettes/brightbox_login/when_default_account_is_passed/does_not_error.yml +3 -3
- data/spec/cassettes/brightbox_login/when_default_account_is_passed/does_not_prompt_to_rerun_the_command.yml +3 -3
- data/spec/cassettes/brightbox_login/when_default_account_is_passed/prompts_for_the_password.yml +3 -3
- data/spec/cassettes/brightbox_login/when_default_account_is_passed/requests_access_tokens.yml +3 -3
- data/spec/cassettes/brightbox_login/when_default_account_is_passed/sets_up_the_config.yml +3 -3
- data/spec/cassettes/brightbox_login/when_no_config_is_present/does_not_error.yml +6 -6
- data/spec/cassettes/brightbox_login/when_no_config_is_present/does_not_prompt_to_rerun_the_command.yml +6 -6
- data/spec/cassettes/brightbox_login/when_no_config_is_present/requests_access_tokens.yml +6 -6
- data/spec/cassettes/brightbox_login/when_no_config_is_present/sets_up_the_config.yml +6 -6
- data/spec/cassettes/brightbox_login/when_no_password_is_given/does_not_error.yml +6 -6
- data/spec/cassettes/brightbox_login/when_no_password_is_given/does_not_prompt_to_rerun_the_command.yml +6 -6
- data/spec/cassettes/brightbox_login/when_no_password_is_given/prompts_for_the_password.yml +6 -6
- data/spec/cassettes/brightbox_login/when_no_password_is_given/requests_access_tokens.yml +6 -6
- data/spec/cassettes/brightbox_login/when_no_password_is_given/sets_up_the_config.yml +6 -6
- data/spec/cassettes/brightbox_sql_instances/create/--allow-access_10_0_0_0/correctly_sends_API_parameters.yml +313 -26
- data/spec/cassettes/brightbox_sql_instances/create/--allow-access_srv-12345_grp-12345/correctly_sends_API_parameters.yml +1204 -38
- data/spec/cassettes/brightbox_sql_instances/create/--engine_mysql/correctly_sends_API_parameters.yml +596 -26
- data/spec/cassettes/brightbox_sql_instances/create/--engine_mysql_--engine-version_5_6/correctly_sends_API_parameters.yml +63 -9
- data/spec/cassettes/brightbox_sql_instances/create/--engine_mysql_--engine-version_8_0/correctly_sends_API_parameters.yml +393 -0
- data/spec/cassettes/brightbox_sql_instances/create/--maintenance-weekday_5_--maintenance_hour_11/correctly_sends_API_parameters.yml +393 -0
- data/spec/cassettes/brightbox_sql_instances/create/--maintenance-weekday_thursday/correctly_sends_API_parameters.yml +393 -0
- data/spec/cassettes/brightbox_sql_instances/create/--snapshot_dbi-12345/includes_schedule_fields_in_response.yml +1466 -0
- data/spec/cassettes/brightbox_sql_instances/create/--snapshots-schedule_0_12_4_/includes_schedule_fields_in_response.yml +342 -0
- data/spec/cassettes/brightbox_sql_instances/create/without_arguments/reports_the_new_admin_password.yml +541 -26
- data/spec/cassettes/brightbox_sql_instances/create/without_arguments/reports_the_new_admin_username.yml +484 -26
- data/spec/cassettes/brightbox_sql_instances/snapshot/when_database_server_active/correctly_sends_API_parameters.yml +4 -4
- data/spec/cassettes/brightbox_sql_instances/snapshot/when_database_server_can_not_be_snapshotted/reports_an_error_to_the_user.yml +2 -2
- data/spec/cassettes/brightbox_sql_snapshots/list/when_resources_are_available/does_not_output_to_stderr.yml +2 -2
- data/spec/cassettes/brightbox_sql_snapshots/list/when_resources_are_available/outputs_table_details_to_stdout.yml +2 -2
- data/spec/cassettes/brightbox_sql_snapshots/show/when_resource_exists/does_not_output_to_stderr.yml +2 -2
- data/spec/commands/accounts/default_spec.rb +1 -2
- data/spec/commands/accounts/list_spec.rb +7 -8
- data/spec/commands/accounts/reset_ftp_password_spec.rb +1 -2
- data/spec/commands/accounts/show_spec.rb +1 -2
- data/spec/commands/cloudips/create_spec.rb +1 -2
- data/spec/commands/cloudips/destroy_spec.rb +1 -2
- data/spec/commands/cloudips/list_spec.rb +1 -2
- data/spec/commands/cloudips/map_spec.rb +2 -3
- data/spec/commands/cloudips/show_spec.rb +1 -2
- data/spec/commands/cloudips/unmap_spec.rb +1 -2
- data/spec/commands/cloudips/update_spec.rb +7 -8
- data/spec/commands/config/client_add_spec.rb +2 -3
- data/spec/commands/config/client_default_spec.rb +1 -2
- data/spec/commands/config/client_list_spec.rb +1 -2
- data/spec/commands/config/client_remove_spec.rb +1 -2
- data/spec/commands/config/user_add_spec.rb +3 -4
- data/spec/commands/firewall_policies/update_spec.rb +3 -3
- data/spec/commands/groups/add_server_spec.rb +1 -2
- data/spec/commands/groups/create_spec.rb +1 -2
- data/spec/commands/groups/destroy_spec.rb +1 -2
- data/spec/commands/groups/list_spec.rb +1 -2
- data/spec/commands/groups/move_servers_spec.rb +1 -2
- data/spec/commands/groups/remove_servers_spec.rb +1 -2
- data/spec/commands/groups/show_spec.rb +1 -2
- data/spec/commands/groups/update_spec.rb +1 -2
- data/spec/commands/images/destroy_spec.rb +1 -2
- data/spec/commands/images/list_spec.rb +62 -63
- data/spec/commands/images/locking_spec.rb +4 -4
- data/spec/commands/images/register_spec.rb +89 -3
- data/spec/commands/images/show_spec.rb +56 -4
- data/spec/commands/images/update_spec.rb +53 -3
- data/spec/commands/lbs/add_nodes_spec.rb +1 -2
- data/spec/commands/lbs/create_spec.rb +2 -3
- data/spec/commands/lbs/destroy_spec.rb +1 -2
- data/spec/commands/lbs/list_spec.rb +1 -2
- data/spec/commands/lbs/locking_spec.rb +4 -4
- data/spec/commands/lbs/remove_nodes_spec.rb +1 -2
- data/spec/commands/lbs/show_spec.rb +1 -2
- data/spec/commands/lbs/update_spec.rb +3 -4
- data/spec/commands/login_spec.rb +134 -30
- data/spec/commands/policies/apply_spec.rb +1 -2
- data/spec/commands/policies/create_spec.rb +1 -2
- data/spec/commands/policies/destroy_spec.rb +1 -2
- data/spec/commands/policies/list_spec.rb +1 -2
- data/spec/commands/policies/remove_spec.rb +1 -2
- data/spec/commands/policies/show_spec.rb +1 -2
- data/spec/commands/policies/update_spec.rb +1 -2
- data/spec/commands/rules/create_spec.rb +1 -2
- data/spec/commands/rules/destroy_spec.rb +1 -2
- data/spec/commands/rules/list_spec.rb +1 -2
- data/spec/commands/rules/show_spec.rb +1 -2
- data/spec/commands/rules/update_spec.rb +1 -2
- data/spec/commands/servers/activate_console_spec.rb +1 -2
- data/spec/commands/servers/create_spec.rb +112 -10
- data/spec/commands/servers/destroy_spec.rb +1 -2
- data/spec/commands/servers/list_spec.rb +1 -2
- data/spec/commands/servers/locking_spec.rb +4 -4
- data/spec/commands/servers/reboot_spec.rb +3 -4
- data/spec/commands/servers/reset_spec.rb +3 -4
- data/spec/commands/servers/show_spec.rb +1 -2
- data/spec/commands/servers/shutdown_spec.rb +1 -2
- data/spec/commands/servers/snapshot_spec.rb +1 -2
- data/spec/commands/servers/start_spec.rb +1 -2
- data/spec/commands/servers/stop_spec.rb +1 -2
- data/spec/commands/servers/update_spec.rb +1 -2
- data/spec/commands/sql/instances/create_spec.rb +58 -75
- data/spec/commands/sql/instances/locking_spec.rb +4 -4
- data/spec/commands/sql/instances/show_spec.rb +7 -7
- data/spec/commands/sql/instances/snapshot_spec.rb +2 -2
- data/spec/commands/sql/instances/update_spec.rb +8 -8
- data/spec/commands/sql/snapshots/list_spec.rb +1 -1
- data/spec/commands/sql/snapshots/locking_spec.rb +4 -4
- data/spec/commands/sql/snapshots/show_spec.rb +1 -1
- data/spec/commands/sql/types/list_spec.rb +1 -2
- data/spec/commands/types/list_spec.rb +1 -2
- data/spec/commands/users/list_spec.rb +1 -2
- data/spec/commands/users/show_spec.rb +1 -2
- data/spec/commands/users/update_spec.rb +1 -2
- data/spec/commands/zones/list_spec.rb +1 -2
- data/spec/configs/api_client.ini +1 -1
- data/spec/configs/user_app.ini +2 -2
- data/spec/spec_helper.rb +16 -3
- data/spec/support/authentication_helpers.rb +98 -0
- data/spec/support/config_helpers.rb +2 -4
- data/spec/support/password_prompt_helpers.rb +22 -1
- data/spec/support/server_helper.rb +5 -5
- data/spec/support/tmp_config.rb +1 -1
- data/spec/support/token_helpers.rb +2 -2
- data/spec/support/vcr.rb +3 -22
- data/spec/unit/brightbox/api/created_on_spec.rb +2 -2
- data/spec/unit/brightbox/api/fog_model_spec.rb +13 -13
- data/spec/unit/brightbox/api/klass_name_spec.rb +0 -1
- data/spec/unit/brightbox/api/method_missing_spec.rb +64 -0
- data/spec/unit/brightbox/api/require_account_spec.rb +0 -1
- data/spec/unit/brightbox/api/respond_to_spec.rb +71 -0
- data/spec/unit/brightbox/bb_config/access_token_filename_spec.rb +0 -1
- data/spec/unit/brightbox/bb_config/account_spec.rb +0 -1
- data/spec/unit/brightbox/bb_config/add_login_spec.rb +27 -28
- data/spec/unit/brightbox/bb_config/add_section_spec.rb +1 -2
- data/spec/unit/brightbox/bb_config/clear_default_client_spec.rb +0 -1
- data/spec/unit/brightbox/bb_config/client_id_spec.rb +0 -1
- data/spec/unit/brightbox/bb_config/client_name_spec.rb +0 -1
- data/spec/unit/brightbox/bb_config/config_directory_exists_spec.rb +0 -1
- data/spec/unit/brightbox/bb_config/config_directory_spec.rb +0 -1
- data/spec/unit/brightbox/bb_config/config_spec.rb +2 -3
- data/spec/unit/brightbox/bb_config/default_account_spec.rb +0 -1
- data/spec/unit/brightbox/bb_config/default_client_spec.rb +0 -1
- data/spec/unit/brightbox/bb_config/delete_section_spec.rb +0 -1
- data/spec/unit/brightbox/bb_config/find_or_set_default_account_spec.rb +4 -4
- data/spec/unit/brightbox/bb_config/refresh_token_filename_spec.rb +0 -1
- data/spec/unit/brightbox/bb_config/renew_tokens_spec.rb +3 -4
- data/spec/unit/brightbox/bb_config/save_default_account_spec.rb +0 -1
- data/spec/unit/brightbox/bb_config/save_spec.rb +0 -1
- data/spec/unit/brightbox/bb_config/section_names_spec.rb +1 -1
- data/spec/unit/brightbox/bb_config/to_fog_spec.rb +2 -2
- data/spec/unit/brightbox/collaborating_account/to_row_spec.rb +3 -3
- data/spec/unit/brightbox/config/api_client/to_fog_spec.rb +8 -8
- data/spec/unit/brightbox/config/api_client/valid_spec.rb +4 -4
- data/spec/unit/brightbox/config/discover_two_factor_pin_spec.rb +87 -0
- data/spec/unit/brightbox/config/section_name_deduplicator_spec.rb +1 -1
- data/spec/unit/brightbox/config/user_application/to_fog_spec.rb +10 -10
- data/spec/unit/brightbox/config/user_application/valid_spec.rb +3 -3
- data/spec/unit/brightbox/connection_manager/fetch_connection_spec.rb +1 -1
- data/spec/unit/brightbox/database_server/clean_arguments_spec.rb +1 -2
- data/spec/unit/brightbox/database_server/maintenance_window_spec.rb +0 -1
- data/spec/unit/brightbox/error_parser/pretty_print_spec.rb +0 -1
- data/spec/unit/brightbox/firewall_policy/apply_to_spec.rb +0 -1
- data/spec/unit/brightbox/firewall_policy/create_spec.rb +0 -1
- data/spec/unit/brightbox/firewall_policy/find_or_call_spec.rb +0 -1
- data/spec/unit/brightbox/firewall_policy/find_spec.rb +0 -1
- data/spec/unit/brightbox/firewall_rule/find_spec.rb +9 -9
- data/spec/unit/brightbox/firewall_rule/from_policy_spec.rb +4 -4
- data/spec/unit/brightbox/legacy/args_adjuster_spec.rb +20 -21
- data/spec/unit/brightbox/server/create_spec.rb +1 -2
- data/spec/unit/brightbox/server/start_spec.rb +2 -2
- data/spec/unit/brightbox/server/update_spec.rb +0 -1
- data/spec/unit/brightbox/user_collaboration/remove_spec.rb +0 -1
- data/spec/unit/nilable_hash_spec.rb +5 -5
- data/spec/unit/ruby_core_ext_spec.rb +3 -4
- data/spec/unit/temporary_home_spec.rb +1 -1
- data/spec/unit/tmp_config_spec.rb +0 -1
- metadata +131 -99
- data/bin/brightbox-accounts +0 -13
- data/bin/brightbox-cloudips +0 -13
- data/bin/brightbox-config +0 -13
- data/bin/brightbox-firewall-policies +0 -13
- data/bin/brightbox-firewall-rules +0 -13
- data/bin/brightbox-groups +0 -13
- data/bin/brightbox-images +0 -13
- data/bin/brightbox-lbs +0 -13
- data/bin/brightbox-servers +0 -13
- data/bin/brightbox-types +0 -13
- data/bin/brightbox-users +0 -13
- data/bin/brightbox-zones +0 -13
- data/lib/brightbox-cli/commands/config/client-default.rb +0 -26
|
@@ -12,11 +12,10 @@ module Brightbox
|
|
|
12
12
|
if defined?(@access_token) && !@access_token.nil?
|
|
13
13
|
return @access_token
|
|
14
14
|
end
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
end
|
|
15
|
+
|
|
16
|
+
@access_token = if File.exist?(access_token_filename)
|
|
17
|
+
cached_access_token
|
|
18
|
+
end
|
|
20
19
|
end
|
|
21
20
|
|
|
22
21
|
def refresh_token_filename
|
|
@@ -28,11 +27,10 @@ module Brightbox
|
|
|
28
27
|
if defined?(@refresh_token) && !@refresh_token.nil?
|
|
29
28
|
return @refresh_token
|
|
30
29
|
end
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
end
|
|
30
|
+
|
|
31
|
+
@refresh_token = if File.exist?(refresh_token_filename)
|
|
32
|
+
cached_refresh_token
|
|
33
|
+
end
|
|
36
34
|
end
|
|
37
35
|
|
|
38
36
|
# @deprecation use access_token instead
|
|
@@ -70,6 +68,7 @@ module Brightbox
|
|
|
70
68
|
# through the process.
|
|
71
69
|
#
|
|
72
70
|
password = options[:password] if options[:password]
|
|
71
|
+
one_time_password = options[:one_time_password] if options[:one_time_password]
|
|
73
72
|
|
|
74
73
|
# To prevent refreshing tokens for the wrong client (using client_name
|
|
75
74
|
# is pretty random) we set it specially
|
|
@@ -82,11 +81,15 @@ module Brightbox
|
|
|
82
81
|
if refresh_token
|
|
83
82
|
begin
|
|
84
83
|
service = update_tokens_with_refresh_token
|
|
85
|
-
rescue Excon::Errors::BadRequest, Excon::Errors::Unauthorized
|
|
84
|
+
rescue Fog::Brightbox::OAuth2::TwoFactorMissingError, Excon::Errors::BadRequest, Excon::Errors::Unauthorized
|
|
86
85
|
service = update_tokens_with_user_credentials
|
|
87
86
|
end
|
|
88
87
|
else
|
|
89
|
-
|
|
88
|
+
begin
|
|
89
|
+
service = update_tokens_with_user_credentials(password: password, one_time_password: one_time_password)
|
|
90
|
+
rescue Fog::Brightbox::OAuth2::TwoFactorMissingError, Excon::Errors::BadRequest, Excon::Errors::Unauthorized
|
|
91
|
+
service = update_tokens_with_user_credentials(password: password)
|
|
92
|
+
end
|
|
90
93
|
end
|
|
91
94
|
else
|
|
92
95
|
service = update_tokens_with_client_credentials
|
|
@@ -95,7 +98,6 @@ module Brightbox
|
|
|
95
98
|
new_access_token = service.access_token
|
|
96
99
|
new_refresh_token = service.refresh_token
|
|
97
100
|
update_stored_tokens(new_access_token, new_refresh_token)
|
|
98
|
-
|
|
99
101
|
rescue Excon::Errors::BadRequest, Excon::Errors::Unauthorized
|
|
100
102
|
error "ERROR: Unable to reauthenticate!"
|
|
101
103
|
ensure
|
|
@@ -115,7 +117,9 @@ module Brightbox
|
|
|
115
117
|
# authenticate with the API.
|
|
116
118
|
#
|
|
117
119
|
def save_access_token(current_access_token)
|
|
118
|
-
if access_token
|
|
120
|
+
if access_token == current_access_token
|
|
121
|
+
debug "Access token remains #{access_token}"
|
|
122
|
+
else
|
|
119
123
|
@access_token = current_access_token
|
|
120
124
|
debug "Attempting to save new access token: #{current_access_token}"
|
|
121
125
|
debug "In memory access token: #{@access_token}"
|
|
@@ -124,8 +128,6 @@ module Brightbox
|
|
|
124
128
|
persist_token(access_token_filename, current_access_token)
|
|
125
129
|
|
|
126
130
|
current_access_token
|
|
127
|
-
else
|
|
128
|
-
debug "Access token remains #{access_token}"
|
|
129
131
|
end
|
|
130
132
|
end
|
|
131
133
|
|
|
@@ -133,7 +135,9 @@ module Brightbox
|
|
|
133
135
|
# request a new access token when current one has expired.
|
|
134
136
|
#
|
|
135
137
|
def save_refresh_token(current_token)
|
|
136
|
-
if refresh_token
|
|
138
|
+
if refresh_token == current_token
|
|
139
|
+
debug "Refresh token remains #{refresh_token}"
|
|
140
|
+
else
|
|
137
141
|
@refresh_token = current_token
|
|
138
142
|
debug "Attempting to save new refresh token: #{current_token}"
|
|
139
143
|
debug "In memory refresh token: #{@refresh_token}"
|
|
@@ -142,8 +146,6 @@ module Brightbox
|
|
|
142
146
|
persist_token(refresh_token_filename, current_token)
|
|
143
147
|
|
|
144
148
|
current_token
|
|
145
|
-
else
|
|
146
|
-
debug "Refresh token remains #{refresh_token}"
|
|
147
149
|
end
|
|
148
150
|
end
|
|
149
151
|
|
|
@@ -177,32 +179,30 @@ module Brightbox
|
|
|
177
179
|
connection
|
|
178
180
|
end
|
|
179
181
|
|
|
180
|
-
|
|
181
|
-
def prompt_for_password
|
|
182
|
-
require "highline"
|
|
183
|
-
highline = HighLine.new
|
|
184
|
-
highline.say("Your API credentials have expired, enter your password to update them.")
|
|
185
|
-
# FIXME: Capture interupts if user aborts
|
|
186
|
-
highline.ask("Enter your password : ") { |q| q.echo = false }
|
|
187
|
-
end
|
|
188
|
-
|
|
189
|
-
def update_tokens_with_user_credentials(password = nil)
|
|
182
|
+
def update_tokens_with_user_credentials(password: nil, one_time_password: nil)
|
|
190
183
|
user_application = Brightbox::Config::UserApplication.new(selected_config, client_name)
|
|
191
184
|
|
|
192
|
-
password
|
|
193
|
-
password ||= password_helper_password
|
|
194
|
-
password ||= prompt_for_password
|
|
195
|
-
|
|
196
|
-
password = extend_with_two_factor_pin(password)
|
|
185
|
+
password = discover_password(password: password, expired: true)
|
|
197
186
|
|
|
198
187
|
# FIXME: options are required to work
|
|
199
188
|
options = {
|
|
200
189
|
:client_id => client_name,
|
|
201
190
|
:email => selected_config["username"],
|
|
202
|
-
:password => password
|
|
191
|
+
:password => password,
|
|
192
|
+
:one_time_password => one_time_password
|
|
203
193
|
}
|
|
204
194
|
|
|
205
|
-
|
|
195
|
+
begin
|
|
196
|
+
user_application.fetch_refresh_token(options)
|
|
197
|
+
rescue Fog::Brightbox::OAuth2::TwoFactorMissingError
|
|
198
|
+
options = {
|
|
199
|
+
:client_id => client_name,
|
|
200
|
+
:email => selected_config["username"],
|
|
201
|
+
:password => password,
|
|
202
|
+
:one_time_password => discover_two_factor_pin
|
|
203
|
+
}
|
|
204
|
+
user_application.fetch_refresh_token(options)
|
|
205
|
+
end
|
|
206
206
|
end
|
|
207
207
|
|
|
208
208
|
def fetch_refresh_token(options)
|
|
@@ -210,7 +210,7 @@ module Brightbox
|
|
|
210
210
|
client_config = config[client_name]
|
|
211
211
|
user_application = Brightbox::Config::UserApplication.new(client_config, client_name)
|
|
212
212
|
# replace this portion with code that actually fetches a token
|
|
213
|
-
client_config[
|
|
213
|
+
client_config["refresh_token"] = user_application.fetch_refresh_token(options)
|
|
214
214
|
save_refresh_token
|
|
215
215
|
end
|
|
216
216
|
|
|
@@ -223,9 +223,7 @@ module Brightbox
|
|
|
223
223
|
def persist_token(filename, token)
|
|
224
224
|
token = "" if token.nil?
|
|
225
225
|
# Write out a token file for this process
|
|
226
|
-
File.
|
|
227
|
-
f.write token
|
|
228
|
-
end
|
|
226
|
+
File.write(filename + ".#{$PID}", token)
|
|
229
227
|
# Move process version into place
|
|
230
228
|
debug "Saving #{token} to #{filename}"
|
|
231
229
|
FileUtils.mv filename + ".#{$PID}", filename
|
|
@@ -258,10 +256,9 @@ module Brightbox
|
|
|
258
256
|
FileUtils.rm(refresh_token_filename) if File.exist?(refresh_token_filename)
|
|
259
257
|
end
|
|
260
258
|
|
|
261
|
-
private
|
|
262
|
-
|
|
263
259
|
def base_token_name
|
|
264
260
|
return nil if client_name.nil?
|
|
261
|
+
|
|
265
262
|
client_name.gsub("/", "_")
|
|
266
263
|
end
|
|
267
264
|
end
|
|
@@ -8,11 +8,9 @@ module Brightbox
|
|
|
8
8
|
|
|
9
9
|
# Is the currently selected config using user application details?
|
|
10
10
|
def using_application?
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
raise NoSelectedClientError, NO_CLIENT_MESSAGE
|
|
15
|
-
end
|
|
11
|
+
raise NoSelectedClientError, NO_CLIENT_MESSAGE unless client_name
|
|
12
|
+
|
|
13
|
+
!config[client_name]["username"].nil?
|
|
16
14
|
end
|
|
17
15
|
|
|
18
16
|
# Does this config have multiple clients defined within?
|
|
@@ -31,6 +29,7 @@ module Brightbox
|
|
|
31
29
|
#
|
|
32
30
|
def client_alias
|
|
33
31
|
return nil if selected_config.nil?
|
|
32
|
+
|
|
34
33
|
# FIXME: The 'alias' field is redundant because we are using the section
|
|
35
34
|
# heading for the not ID value but we worry about it for now
|
|
36
35
|
selected_config["alias"] || client_name
|
|
@@ -61,7 +60,7 @@ module Brightbox
|
|
|
61
60
|
#
|
|
62
61
|
def default_client
|
|
63
62
|
@default_client ||= core_setting("default_client")
|
|
64
|
-
rescue
|
|
63
|
+
rescue StandardError
|
|
65
64
|
nil
|
|
66
65
|
end
|
|
67
66
|
|
|
@@ -76,6 +75,7 @@ module Brightbox
|
|
|
76
75
|
def determine_client(preferred_client = nil)
|
|
77
76
|
return preferred_client unless preferred_client.nil?
|
|
78
77
|
return default_client unless default_client.nil?
|
|
78
|
+
|
|
79
79
|
section_names.first unless section_names.empty?
|
|
80
80
|
nil
|
|
81
81
|
end
|
|
@@ -85,8 +85,8 @@ module Brightbox
|
|
|
85
85
|
# If the prefix is in the client ID (identifier not alias) be +true+
|
|
86
86
|
def config_identifier_match_prefix?(prefix)
|
|
87
87
|
client_id = selected_config["client_id"]
|
|
88
|
-
|
|
89
|
-
rescue
|
|
88
|
+
!!/\A#{prefix}-.*/.match(client_id)
|
|
89
|
+
rescue StandardError
|
|
90
90
|
raise NoSelectedClientError, NO_CLIENT_MESSAGE
|
|
91
91
|
end
|
|
92
92
|
end
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
module Brightbox
|
|
2
2
|
module Config
|
|
3
3
|
module GpgEncryptedPasswords
|
|
4
|
-
|
|
4
|
+
attr_writer :gpg_password
|
|
5
5
|
|
|
6
6
|
def gpg_encrypted_password_filename
|
|
7
7
|
file_name = "#{client_name}.password.gpg"
|
|
@@ -13,11 +13,10 @@ module Brightbox
|
|
|
13
13
|
if defined?(@gpg_password) && !@gpg_password.nil?
|
|
14
14
|
return @gpg_password
|
|
15
15
|
end
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
end
|
|
16
|
+
|
|
17
|
+
@gpg_password = if File.exist?(gpg_encrypted_password_filename)
|
|
18
|
+
gpg_decrypt_password
|
|
19
|
+
end
|
|
21
20
|
end
|
|
22
21
|
|
|
23
22
|
private
|
|
@@ -26,14 +25,13 @@ module Brightbox
|
|
|
26
25
|
def gpg_decrypt_password
|
|
27
26
|
info "INFO: Decrypting #{gpg_encrypted_password_filename} to obtain password"
|
|
28
27
|
begin
|
|
29
|
-
IO
|
|
28
|
+
IO.popen(["gpg", "--decrypt", gpg_encrypted_password_filename], "r") do |io|
|
|
30
29
|
io.read.chomp
|
|
31
30
|
end
|
|
32
31
|
rescue Errno::ENOENT
|
|
33
32
|
nil
|
|
34
33
|
end
|
|
35
34
|
end
|
|
36
|
-
|
|
37
35
|
end
|
|
38
36
|
end
|
|
39
37
|
end
|
|
@@ -1,7 +1,26 @@
|
|
|
1
1
|
module Brightbox
|
|
2
2
|
module Config
|
|
3
3
|
module PasswordHelper
|
|
4
|
-
|
|
4
|
+
ENTER_PASSWORD_PROMPT = "Enter your password : ".freeze
|
|
5
|
+
EXPIRED_TOKEN_PROMPT = "Your API credentials have expired, enter your password to update them.".freeze
|
|
6
|
+
|
|
7
|
+
attr_writer :password_helper_password
|
|
8
|
+
|
|
9
|
+
# {discover_password} will return the first password that can be
|
|
10
|
+
# recovered from either the passed input, encrypted storage, a
|
|
11
|
+
# helper application (if configured) or finally promping.
|
|
12
|
+
#
|
|
13
|
+
# @param password [String] a password given to the method
|
|
14
|
+
# @param expired [Boolean] should the prompt explain tokens have expired?
|
|
15
|
+
# @return [String] the password
|
|
16
|
+
#
|
|
17
|
+
def discover_password(password: nil, expired: false)
|
|
18
|
+
password ||= gpg_password
|
|
19
|
+
password ||= password_helper_password
|
|
20
|
+
password ||= prompt_for_password(expired)
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
private
|
|
5
24
|
|
|
6
25
|
def password_helper_command
|
|
7
26
|
return config[client_name]["password_helper_command"] unless client_name.nil?
|
|
@@ -13,15 +32,11 @@ module Brightbox
|
|
|
13
32
|
return @password_helper_password
|
|
14
33
|
end
|
|
15
34
|
|
|
16
|
-
if password_helper_command
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
@password_helper_password = nil
|
|
20
|
-
end
|
|
35
|
+
@password_helper_password = if password_helper_command
|
|
36
|
+
password_helper_call
|
|
37
|
+
end
|
|
21
38
|
end
|
|
22
39
|
|
|
23
|
-
private
|
|
24
|
-
|
|
25
40
|
def password_helper_call
|
|
26
41
|
info "INFO: Calling password helper to obtain password"
|
|
27
42
|
begin
|
|
@@ -33,6 +48,16 @@ module Brightbox
|
|
|
33
48
|
nil
|
|
34
49
|
end
|
|
35
50
|
end
|
|
51
|
+
|
|
52
|
+
# This asks the user to input their password
|
|
53
|
+
def prompt_for_password(expired)
|
|
54
|
+
require "highline"
|
|
55
|
+
highline = HighLine.new
|
|
56
|
+
highline.say(EXPIRED_TOKEN_PROMPT) if expired
|
|
57
|
+
|
|
58
|
+
# FIXME: Capture interupts if user aborts
|
|
59
|
+
highline.ask(ENTER_PASSWORD_PROMPT) { |q| q.echo = false }
|
|
60
|
+
end
|
|
36
61
|
end
|
|
37
62
|
end
|
|
38
63
|
end
|
|
@@ -43,18 +43,27 @@ module Brightbox
|
|
|
43
43
|
#
|
|
44
44
|
begin
|
|
45
45
|
remove_cached_tokens!
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
46
|
+
begin
|
|
47
|
+
renew_tokens(client_name: config_alias,
|
|
48
|
+
password: password)
|
|
49
|
+
rescue Fog::Brightbox::OAuth2::TwoFactorMissingError
|
|
50
|
+
discover_two_factor_pin
|
|
51
|
+
|
|
52
|
+
renew_tokens(client_name: client_alias,
|
|
53
|
+
password: options[:password],
|
|
54
|
+
one_time_password: current_second_factor)
|
|
55
|
+
end
|
|
50
56
|
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
57
|
+
# Try to determine a default account
|
|
58
|
+
unless default_account == find_or_set_default_account
|
|
59
|
+
info "The default account of #{default_account} has been selected"
|
|
60
|
+
end
|
|
55
61
|
|
|
56
|
-
|
|
57
|
-
|
|
62
|
+
# If only client then set it as the default
|
|
63
|
+
set_default_client(client_alias) unless default_client
|
|
64
|
+
rescue StandardError => e
|
|
65
|
+
error "Something went wrong trying to refresh new tokens #{e.message}"
|
|
66
|
+
end
|
|
58
67
|
|
|
59
68
|
# Ensure all our config changes are now saved
|
|
60
69
|
save
|
|
@@ -98,18 +107,25 @@ module Brightbox
|
|
|
98
107
|
|
|
99
108
|
# Renew tokens via config...
|
|
100
109
|
begin
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
110
|
+
begin
|
|
111
|
+
renew_tokens(client_name: client_alias,
|
|
112
|
+
password: options[:password])
|
|
113
|
+
rescue Fog::Brightbox::OAuth2::TwoFactorMissingError
|
|
114
|
+
renew_tokens(client_name: client_alias,
|
|
115
|
+
password: options[:password],
|
|
116
|
+
one_time_password: discover_two_factor_pin)
|
|
117
|
+
end
|
|
105
118
|
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
119
|
+
# Try to determine a default account
|
|
120
|
+
unless default_account == find_or_set_default_account
|
|
121
|
+
info "The default account of #{default_account} has been selected"
|
|
122
|
+
end
|
|
110
123
|
|
|
111
|
-
|
|
112
|
-
|
|
124
|
+
# If only client then set it as the default
|
|
125
|
+
set_default_client(client_alias) unless default_client
|
|
126
|
+
rescue StandardError => e
|
|
127
|
+
error "Something went wrong trying to refresh new tokens #{e.message}"
|
|
128
|
+
end
|
|
113
129
|
|
|
114
130
|
# Ensure all our config changes are now saved
|
|
115
131
|
save
|
|
@@ -119,16 +135,16 @@ module Brightbox
|
|
|
119
135
|
# persisted to disk.
|
|
120
136
|
#
|
|
121
137
|
def delete_section(name)
|
|
122
|
-
|
|
123
|
-
if default_client == name
|
|
124
|
-
clear_default_client
|
|
125
|
-
end
|
|
126
|
-
# remove from the Ini object
|
|
127
|
-
config.delete_section(name)
|
|
138
|
+
return unless client_named?(name)
|
|
128
139
|
|
|
129
|
-
|
|
130
|
-
|
|
140
|
+
if default_client == name
|
|
141
|
+
clear_default_client
|
|
131
142
|
end
|
|
143
|
+
# remove from the Ini object
|
|
144
|
+
config.delete_section(name)
|
|
145
|
+
|
|
146
|
+
dirty! # to ensure save actually writes to disk
|
|
147
|
+
save
|
|
132
148
|
end
|
|
133
149
|
|
|
134
150
|
# Config data for a named section
|
|
@@ -150,7 +166,7 @@ module Brightbox
|
|
|
150
166
|
#
|
|
151
167
|
def section_names
|
|
152
168
|
# Exclude the global "core" section
|
|
153
|
-
config.sections.reject { |s| %w
|
|
169
|
+
config.sections.reject { |s| %w[core alias].include?(s) }
|
|
154
170
|
end
|
|
155
171
|
|
|
156
172
|
private
|
|
@@ -1,33 +1,31 @@
|
|
|
1
1
|
module Brightbox
|
|
2
2
|
module Config
|
|
3
3
|
module TwoFactorAuth
|
|
4
|
+
ENTER_TWO_FACTOR_PROMPT = "Enter your two factor pin : ".freeze
|
|
4
5
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
6
|
+
attr_accessor :current_second_factor
|
|
7
|
+
|
|
8
|
+
def discover_two_factor_pin
|
|
9
|
+
@two_factor_pin ||= Brightbox.config.two_factor_helper_password
|
|
10
|
+
@two_factor_pin ||= prompt_for_two_factor_pin
|
|
11
|
+
|
|
12
|
+
self.current_second_factor = @two_factor_pin
|
|
11
13
|
end
|
|
12
14
|
|
|
13
15
|
private
|
|
14
16
|
|
|
15
17
|
def two_factor_enabled
|
|
16
|
-
return
|
|
17
|
-
|
|
18
|
+
return false unless client_name.nil?
|
|
19
|
+
return true if config[client_name]["two_factor"] == "true"
|
|
18
20
|
|
|
19
|
-
|
|
20
|
-
if two_factor_enabled
|
|
21
|
-
@two_factor_pin ||= Brightbox.config.two_factor_helper_password
|
|
22
|
-
@two_factor_pin ||= prompt_for_two_factor_pin
|
|
23
|
-
end
|
|
21
|
+
false
|
|
24
22
|
end
|
|
25
23
|
|
|
26
24
|
def prompt_for_two_factor_pin
|
|
27
25
|
require "highline"
|
|
28
26
|
highline = HighLine.new
|
|
29
27
|
# FIXME: Capture interupts if user aborts
|
|
30
|
-
highline.ask(
|
|
28
|
+
highline.ask(ENTER_TWO_FACTOR_PROMPT)
|
|
31
29
|
end
|
|
32
30
|
end
|
|
33
31
|
end
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
module Brightbox
|
|
2
2
|
module Config
|
|
3
3
|
module TwoFactorHelper
|
|
4
|
-
|
|
4
|
+
attr_writer :two_factor_helper_password
|
|
5
5
|
|
|
6
6
|
def two_factor_helper_command
|
|
7
7
|
return config[client_name]["two_factor_helper_command"] unless client_name.nil?
|
|
@@ -13,11 +13,9 @@ module Brightbox
|
|
|
13
13
|
return @two_factor_helper_password
|
|
14
14
|
end
|
|
15
15
|
|
|
16
|
-
if two_factor_helper_command
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
@two_factor_helper_password = nil
|
|
20
|
-
end
|
|
16
|
+
@two_factor_helper_password = if two_factor_helper_command
|
|
17
|
+
two_factor_helper_call
|
|
18
|
+
end
|
|
21
19
|
end
|
|
22
20
|
|
|
23
21
|
private
|
|
@@ -29,7 +27,7 @@ module Brightbox
|
|
|
29
27
|
IO.popen(cmd, "r") do |io|
|
|
30
28
|
io.readline.chomp
|
|
31
29
|
end
|
|
32
|
-
rescue Errno::ENOENT
|
|
30
|
+
rescue ArgumentError, Errno::ENOENT
|
|
33
31
|
nil
|
|
34
32
|
end
|
|
35
33
|
end
|
|
@@ -3,7 +3,7 @@ module Brightbox
|
|
|
3
3
|
class UserApplication
|
|
4
4
|
# FIXME: api_url should use fog's underlying default
|
|
5
5
|
#
|
|
6
|
-
NON_BLANK_KEYS = %w
|
|
6
|
+
NON_BLANK_KEYS = %w[api_url username].freeze
|
|
7
7
|
|
|
8
8
|
attr_accessor :selected_config, :client_name
|
|
9
9
|
|
|
@@ -16,11 +16,12 @@ module Brightbox
|
|
|
16
16
|
check_required_params
|
|
17
17
|
# Note we have to merge in refresh token at the higher level
|
|
18
18
|
{
|
|
19
|
-
:provider =>
|
|
20
|
-
:brightbox_api_url => selected_config[
|
|
21
|
-
:brightbox_auth_url => selected_config[
|
|
19
|
+
:provider => "Brightbox",
|
|
20
|
+
:brightbox_api_url => selected_config["api_url"],
|
|
21
|
+
:brightbox_auth_url => selected_config["auth_url"] || selected_config["api_url"],
|
|
22
22
|
:brightbox_client_id => client_id,
|
|
23
23
|
:brightbox_secret => client_secret,
|
|
24
|
+
:brightbox_support_two_factor => true,
|
|
24
25
|
:persistent => persistent?
|
|
25
26
|
}
|
|
26
27
|
end
|
|
@@ -40,7 +41,9 @@ module Brightbox
|
|
|
40
41
|
#
|
|
41
42
|
def fetch_refresh_token(options)
|
|
42
43
|
password_options = {
|
|
43
|
-
:brightbox_password => options[:password]
|
|
44
|
+
:brightbox_password => options[:password],
|
|
45
|
+
:brightbox_support_two_factor => true,
|
|
46
|
+
:brightbox_one_time_password => options[:one_time_password]
|
|
44
47
|
}
|
|
45
48
|
|
|
46
49
|
default_fog_options = password_auth_params.merge(password_options)
|
|
@@ -64,31 +67,28 @@ module Brightbox
|
|
|
64
67
|
end
|
|
65
68
|
|
|
66
69
|
def persistent?
|
|
67
|
-
|
|
68
|
-
false
|
|
69
|
-
else
|
|
70
|
-
true
|
|
71
|
-
end
|
|
70
|
+
selected_config["persistent"] != "false"
|
|
72
71
|
end
|
|
73
72
|
|
|
74
73
|
def password_auth_params
|
|
75
74
|
{
|
|
76
|
-
:provider =>
|
|
77
|
-
:brightbox_api_url => selected_config[
|
|
78
|
-
:brightbox_auth_url => selected_config[
|
|
75
|
+
:provider => "Brightbox",
|
|
76
|
+
:brightbox_api_url => selected_config["api_url"],
|
|
77
|
+
:brightbox_auth_url => selected_config["auth_url"] || selected_config["api_url"],
|
|
79
78
|
:brightbox_client_id => client_id,
|
|
80
79
|
:brightbox_secret => client_secret,
|
|
81
80
|
:brightbox_username => selected_config["username"],
|
|
81
|
+
:brightbox_support_two_factor => true,
|
|
82
82
|
:persistent => persistent?
|
|
83
83
|
}
|
|
84
84
|
end
|
|
85
85
|
|
|
86
86
|
def check_required_params
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
87
|
+
return if valid?
|
|
88
|
+
|
|
89
|
+
NON_BLANK_KEYS.each do |key|
|
|
90
|
+
unless selected_config.key?(key) && !selected_config[key].to_s.empty?
|
|
91
|
+
raise Brightbox::BBConfigError, "#{key} option missing from config in section #{client_name}"
|
|
92
92
|
end
|
|
93
93
|
end
|
|
94
94
|
end
|