Browse Source

Group policy API-2 HEAT resources: Classifiers, Rules

This is the second patch in the Group Policy resources implementation
series. This patch implements:
    Policy Classifiers
    Policy Actions
    Policy Rules

In the context of larger Group Policy model, the Policy Rule resource
is referenced by Contracts, which will be introduced in the subsequent
patch.

Change-Id: If6df98133bb517ebfba37e20a988d9837aeee7f8
Implements: blueprint group-based-policy-automation
Hemanth Ravi 4 years ago
parent
commit
cbbc6d5546

+ 240
- 0
gbpautomation/heat/engine/resources/neutron/grouppolicy.py View File

@@ -17,6 +17,7 @@ from gbpautomation.heat.engine.resources.neutron import gbpresource
17 17
 from neutronclient.common.exceptions import NeutronClientException
18 18
 
19 19
 from heat.engine import attributes
20
+from heat.engine import constraints
20 21
 from heat.engine import properties
21 22
 
22 23
 
@@ -348,10 +349,249 @@ class L3Policy(gbpresource.GBPResource):
348 349
                 self.resource_id, {'l3_policy': prop_diff})
349 350
 
350 351
 
352
+class PolicyClassifier(gbpresource.GBPResource):
353
+
354
+    PROPERTIES = (
355
+        TENANT_ID, NAME, DESCRIPTION, PROTOCOL, PORT_RANGE,
356
+        DIRECTION
357
+    ) = (
358
+        'tenant_id', 'name', 'description', 'protocol', 'port_range',
359
+        'direction'
360
+    )
361
+
362
+    properties_schema = {
363
+        TENANT_ID: properties.Schema(
364
+            properties.Schema.STRING,
365
+            _('Tenant id of the policy classifier.')
366
+        ),
367
+        NAME: properties.Schema(
368
+            properties.Schema.STRING,
369
+            _('Name of the policy classifier.'),
370
+            update_allowed=True
371
+        ),
372
+        DESCRIPTION: properties.Schema(
373
+            properties.Schema.STRING,
374
+            _('Description of the policy classifier.'),
375
+            update_allowed=True
376
+        ),
377
+        PROTOCOL: properties.Schema(
378
+            properties.Schema.STRING,
379
+            _('Protocol of traffic described by the policy classifier.'),
380
+            constraints=[
381
+                constraints.AllowedValues(['tcp', 'udp', 'icmp', None])
382
+            ],
383
+            update_allowed=True
384
+        ),
385
+        PORT_RANGE: properties.Schema(
386
+            properties.Schema.STRING,
387
+            _('Port range of traffic described by the policy classifier.'),
388
+            update_allowed=True
389
+        ),
390
+        DIRECTION: properties.Schema(
391
+            properties.Schema.STRING,
392
+            _('Direction of traffic described by the policy classifier.'),
393
+            constraints=[
394
+                constraints.AllowedValues(['in', 'out', 'bi', None])
395
+            ],
396
+            update_allowed=True
397
+        )
398
+    }
399
+
400
+    def _show_resource(self):
401
+        client = self.grouppolicy()
402
+        pc_id = self.resource_id
403
+        return client.show_policy_classifier(pc_id)['policy_classifier']
404
+
405
+    def handle_create(self):
406
+        client = self.grouppolicy()
407
+
408
+        props = {}
409
+        for key in self.properties:
410
+            if self.properties.get(key) is not None:
411
+                props[key] = self.properties.get(key)
412
+
413
+        policy_classifier = client.create_policy_classifier(
414
+            {'policy_classifier': props})['policy_classifier']
415
+
416
+        self.resource_id_set(policy_classifier['id'])
417
+
418
+    def handle_delete(self):
419
+
420
+        client = self.grouppolicy()
421
+        pc_id = self.resource_id
422
+
423
+        try:
424
+            client.delete_policy_classifier(pc_id)
425
+        except NeutronClientException as ex:
426
+            self.client_plugin().ignore_not_found(ex)
427
+        else:
428
+            return self._delete_task()
429
+
430
+    def handle_update(self, json_snippet, tmpl_diff, prop_diff):
431
+        if prop_diff:
432
+            self.grouppolicy().update_policy_classifier(
433
+                self.resource_id, {'policy_classifier': prop_diff})
434
+
435
+
436
+class PolicyAction(gbpresource.GBPResource):
437
+
438
+    PROPERTIES = (
439
+        TENANT_ID, NAME, DESCRIPTION, ACTION_TYPE, ACTION_VALUE
440
+    ) = (
441
+        'tenant_id', 'name', 'description', 'action_type', 'action_value'
442
+    )
443
+
444
+    properties_schema = {
445
+        TENANT_ID: properties.Schema(
446
+            properties.Schema.STRING,
447
+            _('Tenant id of the action.')
448
+        ),
449
+        NAME: properties.Schema(
450
+            properties.Schema.STRING,
451
+            _('Name of the action.'),
452
+            update_allowed=True
453
+        ),
454
+        DESCRIPTION: properties.Schema(
455
+            properties.Schema.STRING,
456
+            _('Description of the action.'),
457
+            update_allowed=True
458
+        ),
459
+        ACTION_TYPE: properties.Schema(
460
+            properties.Schema.STRING,
461
+            _('Type of action.'),
462
+            constraints=[
463
+                constraints.AllowedValues(['allow', 'redirect', None])
464
+            ],
465
+            update_allowed=True
466
+        ),
467
+        ACTION_VALUE: properties.Schema(
468
+            properties.Schema.STRING,
469
+            _('Value of the action.'),
470
+            update_allowed=True
471
+        )
472
+    }
473
+
474
+    def _show_resource(self):
475
+        client = self.grouppolicy()
476
+        action_id = self.resource_id
477
+        return client.show_policy_action(action_id)['policy_action']
478
+
479
+    def handle_create(self):
480
+        client = self.grouppolicy()
481
+
482
+        props = {}
483
+        for key in self.properties:
484
+            if self.properties.get(key) is not None:
485
+                props[key] = self.properties.get(key)
486
+
487
+        policy_action = client.create_policy_action(
488
+            {'policy_action': props})['policy_action']
489
+
490
+        self.resource_id_set(policy_action['id'])
491
+
492
+    def handle_delete(self):
493
+
494
+        client = self.grouppolicy()
495
+        action_id = self.resource_id
496
+
497
+        try:
498
+            client.delete_policy_action(action_id)
499
+        except NeutronClientException as ex:
500
+            self.client_plugin().ignore_not_found(ex)
501
+        else:
502
+            return self._delete_task()
503
+
504
+    def handle_update(self, json_snippet, tmpl_diff, prop_diff):
505
+        if prop_diff:
506
+            self.grouppolicy().update_policy_action(
507
+                self.resource_id, {'policy_action': prop_diff})
508
+
509
+
510
+class PolicyRule(gbpresource.GBPResource):
511
+
512
+    PROPERTIES = (
513
+        TENANT_ID, NAME, DESCRIPTION, ENABLED, POLICY_CLASSIFIER_ID,
514
+        POLICY_ACTIONS
515
+    ) = (
516
+        'tenant_id', 'name', 'description', 'enabled', 'policy_classifier_id',
517
+        'policy_actions'
518
+    )
519
+
520
+    properties_schema = {
521
+        TENANT_ID: properties.Schema(
522
+            properties.Schema.STRING,
523
+            _('Tenant id of the policy rule.')
524
+        ),
525
+        NAME: properties.Schema(
526
+            properties.Schema.STRING,
527
+            _('Name of the policy rule.'),
528
+            update_allowed=True
529
+        ),
530
+        DESCRIPTION: properties.Schema(
531
+            properties.Schema.STRING,
532
+            _('Description of the policy rule.'),
533
+            update_allowed=True
534
+        ),
535
+        ENABLED: properties.Schema(
536
+            properties.Schema.BOOLEAN,
537
+            _('State of policy rule.'),
538
+            default=True, update_allowed=True
539
+        ),
540
+        POLICY_CLASSIFIER_ID: properties.Schema(
541
+            properties.Schema.STRING,
542
+            _('Classifier id of the policy rule.'),
543
+            required=True, update_allowed=True
544
+        ),
545
+        POLICY_ACTIONS: properties.Schema(
546
+            properties.Schema.LIST,
547
+            _('List of actions of the policy rule.'),
548
+            default=None, update_allowed=True
549
+        )
550
+    }
551
+
552
+    def _show_resource(self):
553
+        client = self.grouppolicy()
554
+        rule_id = self.resource_id
555
+        return client.show_policy_rule(rule_id)['policy_rule']
556
+
557
+    def handle_create(self):
558
+        client = self.grouppolicy()
559
+
560
+        props = {}
561
+        for key in self.properties:
562
+            if self.properties.get(key) is not None:
563
+                props[key] = self.properties.get(key)
564
+
565
+        policy_rule = client.create_policy_rule(
566
+            {'policy_rule': props})['policy_rule']
567
+
568
+        self.resource_id_set(policy_rule['id'])
569
+
570
+    def handle_delete(self):
571
+
572
+        client = self.grouppolicy()
573
+        rule_id = self.resource_id
574
+
575
+        try:
576
+            client.delete_policy_rule(rule_id)
577
+        except NeutronClientException as ex:
578
+            self.client_plugin().ignore_not_found(ex)
579
+        else:
580
+            return self._delete_task()
581
+
582
+    def handle_update(self, json_snippet, tmpl_diff, prop_diff):
583
+        if prop_diff:
584
+            self.grouppolicy().update_policy_rule(
585
+                self.resource_id, {'policy_rule': prop_diff})
586
+
587
+
351 588
 def resource_mapping():
352 589
     return {
353 590
         'OS::Neutron::Endpoint': Endpoint,
354 591
         'OS::Neutron::EndpointGroup': EndpointGroup,
355 592
         'OS::Neutron::L2Policy': L2Policy,
356 593
         'OS::Neutron::L3Policy': L3Policy,
594
+        'OS::Neutron::PolicyClassifier': PolicyClassifier,
595
+        'OS::Neutron::PolicyAction': PolicyAction,
596
+        'OS::Neutron::PolicyRule': PolicyRule
357 597
     }

+ 397
- 32
gbpautomation/heat/tests/test_grouppolicy.py View File

@@ -11,6 +11,7 @@
11 11
 #    under the License.
12 12
 
13 13
 import copy
14
+import six
14 15
 
15 16
 from gbpautomation.heat.engine.resources.neutron import grouppolicy
16 17
 from gbpclient.v2_0 import client as gbpclient
@@ -104,6 +105,65 @@ l3_policy_template = '''
104 105
 }
105 106
 '''
106 107
 
108
+policy_classifier_template = '''
109
+{
110
+ "AWSTemplateFormatVersion" : "2010-09-09",
111
+  "Description" : "Template to test neutron policy classifier",
112
+  "Parameters" : {},
113
+  "Resources" : {
114
+  "policy_classifier": {
115
+      "Type": "OS::Neutron::PolicyClassifier",
116
+      "Properties": {
117
+                "name": "test-policy-classifier",
118
+                "description": "test policy classifier resource",
119
+                "protocol": "tcp",
120
+                "port_range": "8000-9000",
121
+                "direction": "bi"
122
+        }
123
+     }
124
+  }
125
+}
126
+'''
127
+
128
+policy_action_template = '''
129
+{
130
+ "AWSTemplateFormatVersion" : "2010-09-09",
131
+  "Description" : "Template to test neutron policy action",
132
+  "Parameters" : {},
133
+  "Resources" : {
134
+  "policy_action": {
135
+      "Type": "OS::Neutron::PolicyAction",
136
+      "Properties": {
137
+                "name": "test-policy-action",
138
+                "description": "test policy action resource",
139
+                "action_type": "redirect",
140
+                "action_value": "7890"
141
+        }
142
+     }
143
+  }
144
+}
145
+'''
146
+
147
+policy_rule_template = '''
148
+{
149
+ "AWSTemplateFormatVersion" : "2010-09-09",
150
+  "Description" : "Template to test neutron l3 policy",
151
+  "Parameters" : {},
152
+  "Resources" : {
153
+  "policy_rule": {
154
+      "Type": "OS::Neutron::PolicyRule",
155
+      "Properties": {
156
+          "name": "test-policy-rule",
157
+          "description": "test policy rule resource",
158
+          "enabled": True,
159
+          "policy_classifier_id": "7890",
160
+          "policy_actions": ['3456', '1234']
161
+      }
162
+    }
163
+  }
164
+}
165
+'''
166
+
107 167
 
108 168
 class EndpointTest(HeatTestCase):
109 169
 
@@ -195,7 +255,7 @@ class EndpointTest(HeatTestCase):
195 255
                                   scheduler.TaskRunner(rsrc.delete))
196 256
         self.assertEqual(
197 257
             'NeutronClientException: An unknown exception occurred.',
198
-            str(error))
258
+            six.text_type(error))
199 259
         self.assertEqual((rsrc.DELETE, rsrc.FAILED), rsrc.state)
200 260
         self.m.VerifyAll()
201 261
 
@@ -344,17 +404,6 @@ class EndpointGroupTest(HeatTestCase):
344 404
         self.assertEqual((rsrc.DELETE, rsrc.FAILED), rsrc.state)
345 405
         self.m.VerifyAll()
346 406
 
347
-    def test_attribute_failed(self):
348
-        rsrc = self.create_endpoint_group()
349
-        self.m.ReplayAll()
350
-        scheduler.TaskRunner(rsrc.create)()
351
-        error = self.assertRaises(exception.InvalidTemplateAttribute,
352
-                                  rsrc.FnGetAtt, 'l3_policy_id')
353
-        self.assertEqual(
354
-            'The Referenced Attribute (endpoint_group l3_policy_id) is '
355
-            'incorrect.', str(error))
356
-        self.m.VerifyAll()
357
-
358 407
     def test_update(self):
359 408
         rsrc = self.create_endpoint_group()
360 409
         gbpclient.Client.update_endpoint_group(
@@ -463,17 +512,6 @@ class L2PolicyTest(HeatTestCase):
463 512
         self.assertEqual((rsrc.DELETE, rsrc.FAILED), rsrc.state)
464 513
         self.m.VerifyAll()
465 514
 
466
-    def test_attribute_failed(self):
467
-        rsrc = self.create_l2_policy()
468
-        self.m.ReplayAll()
469
-        scheduler.TaskRunner(rsrc.create)()
470
-        error = self.assertRaises(exception.InvalidTemplateAttribute,
471
-                                  rsrc.FnGetAtt, 'endpoint_id')
472
-        self.assertEqual(
473
-            'The Referenced Attribute (l2_policy endpoint_id) is '
474
-            'incorrect.', str(error))
475
-        self.m.VerifyAll()
476
-
477 515
     def test_update(self):
478 516
         rsrc = self.create_l2_policy()
479 517
         gbpclient.Client.update_l2_policy(
@@ -586,26 +624,353 @@ class L3PolicyTest(HeatTestCase):
586 624
         self.assertEqual((rsrc.DELETE, rsrc.FAILED), rsrc.state)
587 625
         self.m.VerifyAll()
588 626
 
589
-    def test_attribute_failed(self):
627
+    def test_update(self):
590 628
         rsrc = self.create_l3_policy()
629
+        gbpclient.Client.update_l3_policy(
630
+            '5678', {'l3_policy': {'subnet_prefix_length': 28}})
591 631
         self.m.ReplayAll()
592 632
         scheduler.TaskRunner(rsrc.create)()
593
-        error = self.assertRaises(exception.InvalidTemplateAttribute,
594
-                                  rsrc.FnGetAtt, 'subnet_id')
633
+
634
+        update_template = copy.deepcopy(rsrc.t)
635
+        update_template['Properties']['subnet_prefix_length'] = 28
636
+        scheduler.TaskRunner(rsrc.update, update_template)()
637
+
638
+        self.m.VerifyAll()
639
+
640
+
641
+class PolicyClassifierTest(HeatTestCase):
642
+
643
+    def setUp(self):
644
+        super(PolicyClassifierTest, self).setUp()
645
+        self.m.StubOutWithMock(gbpclient.Client,
646
+                               'create_policy_classifier')
647
+        self.m.StubOutWithMock(gbpclient.Client,
648
+                               'delete_policy_classifier')
649
+        self.m.StubOutWithMock(gbpclient.Client,
650
+                               'show_policy_classifier')
651
+        self.m.StubOutWithMock(gbpclient.Client,
652
+                               'update_policy_classifier')
653
+        self.stub_keystoneclient()
654
+
655
+    def create_policy_classifier(self):
656
+        gbpclient.Client.create_policy_classifier({
657
+            'policy_classifier': {
658
+                "name": "test-policy-classifier",
659
+                "description": "test policy classifier resource",
660
+                "protocol": "tcp",
661
+                "port_range": "8000-9000",
662
+                "direction": "bi"
663
+            }
664
+        }).AndReturn({'policy_classifier': {'id': '5678'}})
665
+
666
+        snippet = template_format.parse(policy_classifier_template)
667
+        stack = utils.parse_stack(snippet)
668
+        resource_defns = stack.t.resource_definitions(stack)
669
+        return grouppolicy.PolicyClassifier(
670
+            'policy_classifier', resource_defns['policy_classifier'], stack)
671
+
672
+    def test_create(self):
673
+        rsrc = self.create_policy_classifier()
674
+        self.m.ReplayAll()
675
+        scheduler.TaskRunner(rsrc.create)()
676
+        self.assertEqual((rsrc.CREATE, rsrc.COMPLETE), rsrc.state)
677
+        self.m.VerifyAll()
678
+
679
+    def test_create_failed(self):
680
+        gbpclient.Client.create_policy_classifier({
681
+            'policy_classifier': {
682
+                "name": "test-policy-classifier",
683
+                "description": "test policy classifier resource",
684
+                "protocol": "tcp",
685
+                "port_range": "8000-9000",
686
+                "direction": "bi"
687
+            }
688
+        }).AndRaise(grouppolicy.NeutronClientException())
689
+        self.m.ReplayAll()
690
+
691
+        snippet = template_format.parse(policy_classifier_template)
692
+        stack = utils.parse_stack(snippet)
693
+        resource_defns = stack.t.resource_definitions(stack)
694
+        rsrc = grouppolicy.PolicyClassifier(
695
+            'policy_classifier', resource_defns['policy_classifier'], stack)
696
+
697
+        error = self.assertRaises(exception.ResourceFailure,
698
+                                  scheduler.TaskRunner(rsrc.create))
595 699
         self.assertEqual(
596
-            'The Referenced Attribute (l3_policy subnet_id) is '
597
-            'incorrect.', str(error))
700
+            'NeutronClientException: An unknown exception occurred.',
701
+            str(error))
702
+        self.assertEqual((rsrc.CREATE, rsrc.FAILED), rsrc.state)
703
+        self.m.VerifyAll()
704
+
705
+    def test_delete(self):
706
+        gbpclient.Client.delete_policy_classifier('5678')
707
+        gbpclient.Client.show_policy_classifier('5678').AndRaise(
708
+            grouppolicy.NeutronClientException(status_code=404))
709
+
710
+        rsrc = self.create_policy_classifier()
711
+        self.m.ReplayAll()
712
+        scheduler.TaskRunner(rsrc.create)()
713
+        scheduler.TaskRunner(rsrc.delete)()
714
+        self.assertEqual((rsrc.DELETE, rsrc.COMPLETE), rsrc.state)
715
+        self.m.VerifyAll()
716
+
717
+    def test_delete_already_gone(self):
718
+        gbpclient.Client.delete_policy_classifier('5678').AndRaise(
719
+            grouppolicy.NeutronClientException(status_code=404))
720
+
721
+        rsrc = self.create_policy_classifier()
722
+        self.m.ReplayAll()
723
+        scheduler.TaskRunner(rsrc.create)()
724
+        scheduler.TaskRunner(rsrc.delete)()
725
+        self.assertEqual((rsrc.DELETE, rsrc.COMPLETE), rsrc.state)
726
+        self.m.VerifyAll()
727
+
728
+    def test_delete_failed(self):
729
+        gbpclient.Client.delete_policy_classifier('5678').AndRaise(
730
+            grouppolicy.NeutronClientException(status_code=400))
731
+
732
+        rsrc = self.create_policy_classifier()
733
+        self.m.ReplayAll()
734
+        scheduler.TaskRunner(rsrc.create)()
735
+        error = self.assertRaises(exception.ResourceFailure,
736
+                                  scheduler.TaskRunner(rsrc.delete))
737
+        self.assertEqual(
738
+            'NeutronClientException: An unknown exception occurred.',
739
+            str(error))
740
+        self.assertEqual((rsrc.DELETE, rsrc.FAILED), rsrc.state)
598 741
         self.m.VerifyAll()
599 742
 
600 743
     def test_update(self):
601
-        rsrc = self.create_l3_policy()
602
-        gbpclient.Client.update_l3_policy(
603
-            '5678', {'l3_policy': {'subnet_prefix_length': 28}})
744
+        rsrc = self.create_policy_classifier()
745
+        gbpclient.Client.update_policy_classifier(
746
+            '5678', {'policy_classifier': {'protocol': 'udp'}})
604 747
         self.m.ReplayAll()
605 748
         scheduler.TaskRunner(rsrc.create)()
606 749
 
607 750
         update_template = copy.deepcopy(rsrc.t)
608
-        update_template['Properties']['subnet_prefix_length'] = 28
751
+        update_template['Properties']['protocol'] = 'udp'
752
+        scheduler.TaskRunner(rsrc.update, update_template)()
753
+
754
+        self.m.VerifyAll()
755
+
756
+
757
+class PolicyActionTest(HeatTestCase):
758
+
759
+    def setUp(self):
760
+        super(PolicyActionTest, self).setUp()
761
+        self.m.StubOutWithMock(gbpclient.Client, 'create_policy_action')
762
+        self.m.StubOutWithMock(gbpclient.Client, 'delete_policy_action')
763
+        self.m.StubOutWithMock(gbpclient.Client, 'show_policy_action')
764
+        self.m.StubOutWithMock(gbpclient.Client, 'update_policy_action')
765
+        self.stub_keystoneclient()
766
+
767
+    def create_policy_action(self):
768
+        gbpclient.Client.create_policy_action({
769
+            'policy_action': {
770
+                "name": "test-policy-action",
771
+                "description": "test policy action resource",
772
+                "action_type": "redirect",
773
+                "action_value": "7890"
774
+            }
775
+        }).AndReturn({'policy_action': {'id': '5678'}})
776
+
777
+        snippet = template_format.parse(policy_action_template)
778
+        stack = utils.parse_stack(snippet)
779
+        resource_defns = stack.t.resource_definitions(stack)
780
+        return grouppolicy.PolicyAction(
781
+            'policy_action', resource_defns['policy_action'], stack)
782
+
783
+    def test_create(self):
784
+        rsrc = self.create_policy_action()
785
+        self.m.ReplayAll()
786
+        scheduler.TaskRunner(rsrc.create)()
787
+        self.assertEqual((rsrc.CREATE, rsrc.COMPLETE), rsrc.state)
788
+        self.m.VerifyAll()
789
+
790
+    def test_create_failed(self):
791
+        gbpclient.Client.create_policy_action({
792
+            'policy_action': {
793
+                "name": "test-policy-action",
794
+                "description": "test policy action resource",
795
+                "action_type": "redirect",
796
+                "action_value": "7890"
797
+            }
798
+        }).AndRaise(grouppolicy.NeutronClientException())
799
+        self.m.ReplayAll()
800
+
801
+        snippet = template_format.parse(policy_action_template)
802
+        stack = utils.parse_stack(snippet)
803
+        resource_defns = stack.t.resource_definitions(stack)
804
+        rsrc = grouppolicy.PolicyAction(
805
+            'policy_action', resource_defns['policy_action'], stack)
806
+
807
+        error = self.assertRaises(exception.ResourceFailure,
808
+                                  scheduler.TaskRunner(rsrc.create))
809
+        self.assertEqual(
810
+            'NeutronClientException: An unknown exception occurred.',
811
+            str(error))
812
+        self.assertEqual((rsrc.CREATE, rsrc.FAILED), rsrc.state)
813
+        self.m.VerifyAll()
814
+
815
+    def test_delete(self):
816
+        gbpclient.Client.delete_policy_action('5678')
817
+        gbpclient.Client.show_policy_action('5678').AndRaise(
818
+            grouppolicy.NeutronClientException(status_code=404))
819
+
820
+        rsrc = self.create_policy_action()
821
+        self.m.ReplayAll()
822
+        scheduler.TaskRunner(rsrc.create)()
823
+        scheduler.TaskRunner(rsrc.delete)()
824
+        self.assertEqual((rsrc.DELETE, rsrc.COMPLETE), rsrc.state)
825
+        self.m.VerifyAll()
826
+
827
+    def test_delete_already_gone(self):
828
+        gbpclient.Client.delete_policy_action('5678').AndRaise(
829
+            grouppolicy.NeutronClientException(status_code=404))
830
+
831
+        rsrc = self.create_policy_action()
832
+        self.m.ReplayAll()
833
+        scheduler.TaskRunner(rsrc.create)()
834
+        scheduler.TaskRunner(rsrc.delete)()
835
+        self.assertEqual((rsrc.DELETE, rsrc.COMPLETE), rsrc.state)
836
+        self.m.VerifyAll()
837
+
838
+    def test_delete_failed(self):
839
+        gbpclient.Client.delete_policy_action('5678').AndRaise(
840
+            grouppolicy.NeutronClientException(status_code=400))
841
+
842
+        rsrc = self.create_policy_action()
843
+        self.m.ReplayAll()
844
+        scheduler.TaskRunner(rsrc.create)()
845
+        error = self.assertRaises(exception.ResourceFailure,
846
+                                  scheduler.TaskRunner(rsrc.delete))
847
+        self.assertEqual(
848
+            'NeutronClientException: An unknown exception occurred.',
849
+            str(error))
850
+        self.assertEqual((rsrc.DELETE, rsrc.FAILED), rsrc.state)
851
+        self.m.VerifyAll()
852
+
853
+    def test_update(self):
854
+        rsrc = self.create_policy_action()
855
+        gbpclient.Client.update_policy_action(
856
+            '5678', {'policy_action': {'action_type': 'allow'}})
857
+        self.m.ReplayAll()
858
+        scheduler.TaskRunner(rsrc.create)()
859
+
860
+        update_template = copy.deepcopy(rsrc.t)
861
+        update_template['Properties']['action_type'] = 'allow'
862
+        scheduler.TaskRunner(rsrc.update, update_template)()
863
+
864
+        self.m.VerifyAll()
865
+
866
+
867
+class PolicyRuleTest(HeatTestCase):
868
+
869
+    def setUp(self):
870
+        super(PolicyRuleTest, self).setUp()
871
+        self.m.StubOutWithMock(gbpclient.Client, 'create_policy_rule')
872
+        self.m.StubOutWithMock(gbpclient.Client, 'delete_policy_rule')
873
+        self.m.StubOutWithMock(gbpclient.Client, 'show_policy_rule')
874
+        self.m.StubOutWithMock(gbpclient.Client, 'update_policy_rule')
875
+        self.stub_keystoneclient()
876
+
877
+    def create_policy_rule(self):
878
+        gbpclient.Client.create_policy_rule({
879
+            'policy_rule': {
880
+                "name": "test-policy-rule",
881
+                "description": "test policy rule resource",
882
+                "enabled": True,
883
+                "policy_classifier_id": "7890",
884
+                "policy_actions": ['3456', '1234']
885
+            }
886
+        }).AndReturn({'policy_rule': {'id': '5678'}})
887
+
888
+        snippet = template_format.parse(policy_rule_template)
889
+        stack = utils.parse_stack(snippet)
890
+        resource_defns = stack.t.resource_definitions(stack)
891
+        return grouppolicy.PolicyRule(
892
+            'policy_rule', resource_defns['policy_rule'], stack)
893
+
894
+    def test_create(self):
895
+        rsrc = self.create_policy_rule()
896
+        self.m.ReplayAll()
897
+        scheduler.TaskRunner(rsrc.create)()
898
+        self.assertEqual((rsrc.CREATE, rsrc.COMPLETE), rsrc.state)
899
+        self.m.VerifyAll()
900
+
901
+    def test_create_failed(self):
902
+        gbpclient.Client.create_policy_rule({
903
+            'policy_rule': {
904
+                "name": "test-policy-rule",
905
+                "description": "test policy rule resource",
906
+                "enabled": True,
907
+                "policy_classifier_id": "7890",
908
+                "policy_actions": ['3456', '1234']
909
+            }
910
+        }).AndRaise(grouppolicy.NeutronClientException())
911
+        self.m.ReplayAll()
912
+
913
+        snippet = template_format.parse(policy_rule_template)
914
+        stack = utils.parse_stack(snippet)
915
+        resource_defns = stack.t.resource_definitions(stack)
916
+        rsrc = grouppolicy.PolicyRule(
917
+            'policy_rule', resource_defns['policy_rule'], stack)
918
+
919
+        error = self.assertRaises(exception.ResourceFailure,
920
+                                  scheduler.TaskRunner(rsrc.create))
921
+        self.assertEqual(
922
+            'NeutronClientException: An unknown exception occurred.',
923
+            str(error))
924
+        self.assertEqual((rsrc.CREATE, rsrc.FAILED), rsrc.state)
925
+        self.m.VerifyAll()
926
+
927
+    def test_delete(self):
928
+        gbpclient.Client.delete_policy_rule('5678')
929
+        gbpclient.Client.show_policy_rule('5678').AndRaise(
930
+            grouppolicy.NeutronClientException(status_code=404))
931
+
932
+        rsrc = self.create_policy_rule()
933
+        self.m.ReplayAll()
934
+        scheduler.TaskRunner(rsrc.create)()
935
+        scheduler.TaskRunner(rsrc.delete)()
936
+        self.assertEqual((rsrc.DELETE, rsrc.COMPLETE), rsrc.state)
937
+        self.m.VerifyAll()
938
+
939
+    def test_delete_already_gone(self):
940
+        gbpclient.Client.delete_policy_rule('5678').AndRaise(
941
+            grouppolicy.NeutronClientException(status_code=404))
942
+
943
+        rsrc = self.create_policy_rule()
944
+        self.m.ReplayAll()
945
+        scheduler.TaskRunner(rsrc.create)()
946
+        scheduler.TaskRunner(rsrc.delete)()
947
+        self.assertEqual((rsrc.DELETE, rsrc.COMPLETE), rsrc.state)
948
+        self.m.VerifyAll()
949
+
950
+    def test_delete_failed(self):
951
+        gbpclient.Client.delete_policy_rule('5678').AndRaise(
952
+            grouppolicy.NeutronClientException(status_code=400))
953
+
954
+        rsrc = self.create_policy_rule()
955
+        self.m.ReplayAll()
956
+        scheduler.TaskRunner(rsrc.create)()
957
+        error = self.assertRaises(exception.ResourceFailure,
958
+                                  scheduler.TaskRunner(rsrc.delete))
959
+        self.assertEqual(
960
+            'NeutronClientException: An unknown exception occurred.',
961
+            str(error))
962
+        self.assertEqual((rsrc.DELETE, rsrc.FAILED), rsrc.state)
963
+        self.m.VerifyAll()
964
+
965
+    def test_update(self):
966
+        rsrc = self.create_policy_rule()
967
+        gbpclient.Client.update_policy_rule(
968
+            '5678', {'policy_rule': {'enabled': False}})
969
+        self.m.ReplayAll()
970
+        scheduler.TaskRunner(rsrc.create)()
971
+
972
+        update_template = copy.deepcopy(rsrc.t)
973
+        update_template['Properties']['enabled'] = False
609 974
         scheduler.TaskRunner(rsrc.update, update_template)()
610 975
 
611 976
         self.m.VerifyAll()

Loading…
Cancel
Save