github.com/niedbalski/juju@v0.0.0-20190215020005-8ff100488e47/acceptancetests/assess_block.py (about)

     1  #!/usr/bin/env python
     2  """Assess juju blocks prevent users from making changes and models"""
     3  
     4  from __future__ import print_function
     5  
     6  import argparse
     7  import logging
     8  import sys
     9  
    10  from assess_min_version import (
    11      JujuAssertionError
    12      )
    13  from deploy_stack import (
    14      BootstrapManager,
    15      deploy_dummy_stack,
    16      )
    17  from utility import (
    18      add_basic_testing_arguments,
    19      configure_logging,
    20      )
    21  
    22  
    23  __metaclass__ = type
    24  
    25  
    26  log = logging.getLogger("assess_block")
    27  
    28  
    29  def make_block_list(client, disabled_commands):
    30      """Return a manually made list of blocks and their status
    31  
    32      :param client: The client whose rules will be used.
    33      :param disabled_commands: list of client.command_set_* elements to
    34          include in simulated output.
    35      """
    36      if not disabled_commands:
    37          return []
    38  
    39      return [{'command-set': ','.join(disabled_commands)}]
    40  
    41  
    42  def test_disabled(client, command, args, include_e=True):
    43      """Test if a command is disabled as expected"""
    44      try:
    45          if command == 'deploy':
    46              client.deploy(args)
    47          elif command == 'remove-service':
    48              client.remove_service(args)
    49          else:
    50              client.juju(command, args, include_e=include_e)
    51          raise JujuAssertionError()
    52      except Exception:
    53          pass
    54  
    55  
    56  def assess_block_destroy_model(client, charm_series):
    57      """Test disabling the destroy-model command.
    58  
    59      When "disable-command destroy-model" is set,
    60      the model cannot be destroyed, but objects
    61      can be added, related, and removed.
    62      """
    63      client.disable_command(client.destroy_model_command)
    64      block_list = client.list_disabled_commands()
    65      if block_list != make_block_list(
    66              client, [client.command_set_destroy_model]):
    67          raise JujuAssertionError(block_list)
    68      test_disabled(
    69          client, client.destroy_model_command,
    70          ('-y', client.env.environment), include_e=False)
    71      # Adding, relating, and removing are not blocked.
    72      deploy_dummy_stack(client, charm_series)
    73  
    74  
    75  def assess_block_remove_object(client, charm_series):
    76      """Test block remove-object
    77  
    78      When "disable-command remove-object" is set,
    79      objects can be added and related, but they
    80      cannot be removed or the model/environment deleted.
    81      """
    82      client.disable_command(client.command_set_remove_object)
    83      block_list = client.list_disabled_commands()
    84      if block_list != make_block_list(
    85              client, [client.command_set_remove_object]):
    86          raise JujuAssertionError(block_list)
    87      test_disabled(
    88          client, client.destroy_model_command,
    89          ('-y', client.env.environment), include_e=False)
    90      # Adding and relating are not blocked.
    91      deploy_dummy_stack(client, charm_series)
    92      test_disabled(client, 'remove-service', 'dummy-source')
    93      test_disabled(client, 'remove-unit', ('dummy-source/1',))
    94      test_disabled(client, 'remove-relation', ('dummy-source', 'dummy-sink'))
    95  
    96  
    97  def assess_block_all_changes(client, charm_series):
    98      """Test Block Functionality: block all-changes"""
    99      client.juju('remove-relation', ('dummy-source', 'dummy-sink'))
   100      client.disable_command(client.command_set_all)
   101      block_list = client.list_disabled_commands()
   102      if block_list != make_block_list(client, [client.command_set_all]):
   103          raise JujuAssertionError(block_list)
   104      test_disabled(client, 'add-relation', ('dummy-source', 'dummy-sink'))
   105      test_disabled(client, 'unexpose', ('dummy-sink',))
   106      test_disabled(client, 'remove-service', 'dummy-sink')
   107      client.enable_command(client.command_set_all)
   108      client.juju('unexpose', ('dummy-sink',))
   109      client.disable_command(client.command_set_all)
   110      test_disabled(client, 'expose', ('dummy-sink',))
   111      client.enable_command(client.command_set_all)
   112      client.remove_service('dummy-sink')
   113      client.wait_for_started()
   114      client.disable_command(client.command_set_all)
   115      test_disabled(client, 'deploy', ('dummy-sink',))
   116      test_disabled(
   117          client, client.destroy_model_command,
   118          ('-y', client.env.environment), include_e=False)
   119  
   120  
   121  def assess_unblock(client, type):
   122      """Test Block Functionality
   123      unblock destroy-model/remove-object/all-changes."""
   124      client.enable_command(type)
   125      block_list = client.list_disabled_commands()
   126      if block_list != make_block_list(client, []):
   127          raise JujuAssertionError(block_list)
   128      if type == client.destroy_model_command:
   129          client.remove_service('dummy-source')
   130          client.wait_for_started()
   131          client.remove_service('dummy-sink')
   132          client.wait_for_started()
   133  
   134  
   135  def assess_block(client, charm_series):
   136      """Test Block Functionality:
   137      block/unblock destroy-model/remove-object/all-changes.
   138      """
   139      log.info('Test started')
   140      block_list = client.list_disabled_commands()
   141      client.wait_for_started()
   142      expected_none_blocked = make_block_list(client, [])
   143      if block_list != expected_none_blocked:
   144          log.error('Controller is not in the expected starting state')
   145          raise JujuAssertionError(
   146              'Expected {}\nFound {}'.format(expected_none_blocked, block_list))
   147      assess_block_destroy_model(client, charm_series)
   148      assess_unblock(client, client.destroy_model_command)
   149      assess_block_remove_object(client, charm_series)
   150      assess_unblock(client, client.command_set_remove_object)
   151      assess_block_all_changes(client, charm_series)
   152      assess_unblock(client, client.command_set_all)
   153      log.info('Test PASS')
   154  
   155  
   156  def parse_args(argv):
   157      """Parse all arguments."""
   158      parser = argparse.ArgumentParser(description="Test Block Functionality")
   159      add_basic_testing_arguments(parser)
   160      parser.set_defaults(series='trusty')
   161      return parser.parse_args(argv)
   162  
   163  
   164  def main(argv=None):
   165      args = parse_args(argv)
   166      configure_logging(args.verbose)
   167      bs_manager = BootstrapManager.from_args(args)
   168      with bs_manager.booted_context(args.upload_tools):
   169          assess_block(bs_manager.client, bs_manager.series)
   170      return 0
   171  
   172  
   173  if __name__ == '__main__':
   174      sys.exit(main())