From 3e7eaee594f4ea6510db759b01b250b0faaf7dca Mon Sep 17 00:00:00 2001 From: Alexander Tivelkov Date: Wed, 30 Apr 2014 17:48:09 +0400 Subject: [PATCH] Basic Security Groups implementation Change-Id: I6a7f9953206f28b2b1fa6223bcceab60ddaadb13 Closes-bug: #1308623 --- .../api/v1/DummyTestApp/Classes/Dummy.yaml | 8 +++ .../Classes/NewNetwork.yaml | 5 ++ meta/io.murano/Classes/Environment.yaml | 6 ++ .../Classes/SecurityGroupManager.yaml | 69 +++++++++++++++++++ .../io.murano/Classes/resources/Instance.yaml | 55 +++++++++++++-- meta/io.murano/Classes/resources/Network.yaml | 6 ++ meta/io.murano/manifest.yaml | 2 + 7 files changed, 146 insertions(+), 5 deletions(-) create mode 100644 meta/io.murano/Classes/SecurityGroupManager.yaml diff --git a/functionaltests/api/v1/DummyTestApp/Classes/Dummy.yaml b/functionaltests/api/v1/DummyTestApp/Classes/Dummy.yaml index 0f3d7859..d25d5f3e 100644 --- a/functionaltests/api/v1/DummyTestApp/Classes/Dummy.yaml +++ b/functionaltests/api/v1/DummyTestApp/Classes/Dummy.yaml @@ -26,8 +26,16 @@ Properties: Default: P@ssw0rd Workflow: + initialize: + Body: + - $.environment: $.find(std:Environment).require() + - $.resources: new(sys:Resources) + deploy: Body: + - $securityGroupIngress: $.resources.json('DomainSecurity.json') + - $.environment.securityGroups.addGroupIngress($securityGroupIngress) + - $.primaryController.deploy() - $.secondaryControllers.pselect($.deploy()) - $.reportDeployed(title => 'Dummy', diff --git a/meta/io.murano.lib.networks.Neutron/Classes/NewNetwork.yaml b/meta/io.murano.lib.networks.Neutron/Classes/NewNetwork.yaml index 38dd0480..715b783e 100644 --- a/meta/io.murano.lib.networks.Neutron/Classes/NewNetwork.yaml +++ b/meta/io.murano.lib.networks.Neutron/Classes/NewNetwork.yaml @@ -54,6 +54,9 @@ Workflow: - assignFloatingIp: Contract: $.bool().notNull() Default: false + - securityGroupName: + Contract: $.string() + Default: null Body: - $.ensureNetworkConfigured() - $portname: $instance.name + '-port-to-' + $.id() @@ -64,6 +67,8 @@ Workflow: Properties: network_id: {Ref: $.net_res_name} fixed_ips: [{subnet_id: {Ref: $.subnet_res_name}}] + security_groups: + - Ref: $securityGroupName $instance.name: Properties: NetworkInterfaces: diff --git a/meta/io.murano/Classes/Environment.yaml b/meta/io.murano/Classes/Environment.yaml index fd6527a0..0c2a199c 100644 --- a/meta/io.murano/Classes/Environment.yaml +++ b/meta/io.murano/Classes/Environment.yaml @@ -30,6 +30,10 @@ Properties: flat: $.class(res:Network) Usage: In + securityGroupManager: + Contract: $.class(sys:SecurityGroupManager) + Usage: Runtime + Workflow: initialize: Body: @@ -37,6 +41,8 @@ Workflow: - $this.stack: new(sys:HeatStack, name => $.name) - $this.instanceNotifier: new(sys:InstanceNotifier, environment => $this) - $this.reporter: new(sys:StatusReporter, environment => $this) + - $this.securityGroupManager: new(sys:SecurityGroupManager, environment => $this) + deploy: Body: diff --git a/meta/io.murano/Classes/SecurityGroupManager.yaml b/meta/io.murano/Classes/SecurityGroupManager.yaml new file mode 100644 index 00000000..5256ea28 --- /dev/null +++ b/meta/io.murano/Classes/SecurityGroupManager.yaml @@ -0,0 +1,69 @@ +Namespaces: + =: io.murano.system + std: io.murano + +Name: SecurityGroupManager + +Properties: + environment: + Contract: $.class(std:Environment).notNull() + + defaultGroupName: + Contract: $.string() + Usage: Runtime + Default: format('MuranoSecurityGroup-{0}', $.environment.name) + +Workflow: + addGroupIngress: + Arguments: + - rules: + Contract: + - FromPort: $.int().notNull() + ToPort: $.int().notNull() + IpProtocol: $.string().notNull() + External: $.bool().notNull() + - groupName: + Contract: $.string().notNull() + Default: $this.defaultGroupName + Body: + - $ext_keys: + true: + ext_key: remote_ip_prefix + ext_val: '0.0.0.0/0' + false: + ext_key: remote_mode + ext_val: remote_group_id + + - $stack: $.environment.stack + - $template: + Resources: + $groupName: + Type: 'OS::Neutron::SecurityGroup' + Properties: + description: format('Composite security group of Murano environment {0}', $.environment.name) + rules: + - port_range_min: null + port_range_max: null + protocol: icmp + remote_ip_prefix: '0.0.0.0/0' + - $.environment.stack.updateTemplate($template) + + - $ingress: $rules.select(dict( + port_range_min => $.FromPort, + port_range_max => $.ToPort, + protocol => $.IpProtocol, + $ext_keys.get($.External).ext_key => $ext_keys.get($.External).ext_val + )) + + - $template: + Resources: + $groupName: + Type: 'OS::Neutron::SecurityGroup' + Properties: + rules: $ingress + - $.environment.stack.updateTemplate($template) + + + + + diff --git a/meta/io.murano/Classes/resources/Instance.yaml b/meta/io.murano/Classes/resources/Instance.yaml index 4465e131..0526cc5d 100644 --- a/meta/io.murano/Classes/resources/Instance.yaml +++ b/meta/io.murano/Classes/resources/Instance.yaml @@ -39,6 +39,9 @@ Properties: floatingIpAddress: Contract: $.string() Usage: Out + securityGroupName: + Contract: $.string() + Default: null Workflow: initialize: @@ -49,15 +52,22 @@ Workflow: deploy: Body: + - $securityGroupName: coalesce( + $.securityGroupName, + $.environment.securityGroupManager.defaultGroupName + ) + - $.createDefaultInstanceSecurityGroupRules($securityGroupName) + - If: $.networks.useEnvironmentNetwork Then: - $.joinNet($.environment.defaultNetworks.environment) + $.joinNet($.environment.defaultNetworks.environment, $securityGroupName) - If: $.networks.useFlatNetwork Then: - $.joinNet($.environment.defaultNetworks.flat) - - $.networks.customNetworks.select($this.joinNet($)) + $.joinNet($.environment.defaultNetworks.flat, $securityGroupName) + - $.networks.customNetworks.select($this.joinNet($, $securityGroupName)) - $userData: $.prepareUserData() + - $template: Resources: $.name: @@ -67,7 +77,8 @@ Workflow: ImageId: $.image UserData: $userData KeyName: $.keyname - + + Outputs: format('{0}-PublicIp', $.name): Value: @@ -83,6 +94,8 @@ Workflow: Arguments: - net: Contract: $.class(Network) + - securityGroupName: + Contract: $.string() Body: - If: $net != null Then: @@ -92,7 +105,7 @@ Workflow: - $.setAttr(fipAssigned, true) Else: - $assignFip: false - - $net.addHostToNetwork($, $assignFip) + - $net.addHostToNetwork($, $assignFip, $securityGroupName) destroy: Body: @@ -105,8 +118,40 @@ Workflow: - $.environment.stack.push() - $.environment.instanceNotifier.untrackApplication($this) + createDefaultInstanceSecurityGroupRules: + Arguments: + - groupName: + Contract: $.string().notNull() + Body: + # TODO: This is a temporary (and quite dirty) workaround. It should be + # implemented using polymorphism, by overriding parts of this method in + # derived classes related to particular OS type + # However bug #1314618 does not allow to do it + + - If: !yaql "'w' in toLower($.image)" + Then: + - $rules: + - ToPort: 3389 + IpProtocol: tcp + FromPort: 3389 + External: true + Else: + - $rules: + - ToPort: 22 + IpProtocol: tcp + FromPort: 22 + External: true + - $.environment.securityGroupManager.addGroupIngress( + rules => $rules, groupName => $groupName) + + getDefaultSecurityRules: prepareUserData: Body: + # TODO: This is a temporary (and quite dirty) workaround. It should be + # implemented using polymorphism, by overriding parts of this method in + # derived classes related to particular OS type + # However bug #1314618 does not allow to do it + - If: !yaql "'w' in toLower($.image)" Then: - $configFile: $.resources.string('Agent-v1.template') diff --git a/meta/io.murano/Classes/resources/Network.yaml b/meta/io.murano/Classes/resources/Network.yaml index 674719f8..f2b72aab 100644 --- a/meta/io.murano/Classes/resources/Network.yaml +++ b/meta/io.murano/Classes/resources/Network.yaml @@ -8,3 +8,9 @@ Workflow: Arguments: - instance: Contract: $.class(Instance).notNull() + - assignFloatingIp: + Contract: $.bool().notNull() + Default: false + - securityGroupName: + Contract: $.string() + Default: null diff --git a/meta/io.murano/manifest.yaml b/meta/io.murano/manifest.yaml index 1895218b..b053235f 100644 --- a/meta/io.murano/manifest.yaml +++ b/meta/io.murano/manifest.yaml @@ -18,5 +18,7 @@ Classes: io.murano.Environment: Environment.yaml io.murano.Application: Application.yaml + io.murano.system.SecurityGroupManager: SecurityGroupManager.yaml + io.murano.resources.Network: resources/Network.yaml io.murano.resources.Instance: resources/Instance.yaml