9
9
is_intrinsic_if ,
10
10
is_intrinsic_no_value ,
11
11
validate_intrinsic_if_items ,
12
+ make_combined_condition ,
13
+ ref ,
14
+ fnGetAtt
12
15
)
13
16
from samtranslator .model .update_policy import UpdatePolicy
14
17
from samtranslator .translator .arn_generator import ArnGenerator
27
30
"Linear10PercentEvery10Minutes" ,
28
31
"AllAtOnce" ,
29
32
]
33
+ CODE_DEPLOY_CONDITION_NAME = "ServerlessCodeDeployCondition"
30
34
31
35
32
36
class DeploymentPreferenceCollection (object ):
@@ -41,12 +45,10 @@ class DeploymentPreferenceCollection(object):
41
45
42
46
def __init__ (self ):
43
47
"""
44
- This collection stores an intenral dict of the deployment preferences for each function's
45
- deployment preference in the SAM Template.
48
+ This collection stores an internal dict of the deployment preferences for each function's
49
+ deployment preference in the SAM Template.
46
50
"""
47
51
self ._resource_preferences = {}
48
- self .codedeploy_application = self ._codedeploy_application ()
49
- self .codedeploy_iam_role = self ._codedeploy_iam_role ()
50
52
51
53
def add (self , logical_id , deployment_preference_dict , condition = None ):
52
54
"""
@@ -93,20 +95,47 @@ def needs_resource_condition(self):
93
95
If all preferences have a condition, all code deploy resources need to be conditionally created
94
96
:return: True, if a condition needs to be created
95
97
"""
96
- return all (preference .condition for preference in self ._resource_preferences .values ())
98
+ # If there are any enabled deployment preferences without conditions, return false
99
+ return self ._resource_preferences and not any (
100
+ not preference .condition and preference .enabled for preference in self ._resource_preferences .values ()
101
+ )
102
+
103
+ def get_all_deployment_conditions (self ):
104
+ """
105
+ Returns a list of all conditions associated with the deployment preference resources
106
+ :return: List of condition names
107
+ """
108
+ conditions_set = set ([preference .condition for preference in self ._resource_preferences .values ()])
109
+ if None in conditions_set :
110
+ # None can exist if there are disabled deployment preference(s)
111
+ conditions_set .remove (None )
112
+ return list (conditions_set )
113
+
114
+ def create_aggregate_deployment_condition (self ):
115
+ """
116
+ Creates an aggregate deployment condition if necessary
117
+ :return: None if <2 conditions are found, otherwise a dictionary of new conditions to add to template
118
+ """
119
+ return make_combined_condition (self .get_all_deployment_conditions (), CODE_DEPLOY_CONDITION_NAME )
97
120
98
121
def enabled_logical_ids (self ):
99
122
"""
100
123
:return: only the logical id's for the deployment preferences in this collection which are enabled
101
124
"""
102
125
return [logical_id for logical_id , preference in self ._resource_preferences .items () if preference .enabled ]
103
126
104
- def _codedeploy_application (self ):
127
+ def get_codedeploy_application (self ):
105
128
codedeploy_application_resource = CodeDeployApplication (CODEDEPLOY_APPLICATION_LOGICAL_ID )
106
129
codedeploy_application_resource .ComputePlatform = "Lambda"
130
+ if self .needs_resource_condition ():
131
+ conditions = self .get_all_deployment_conditions ()
132
+ condition_name = CODE_DEPLOY_CONDITION_NAME
133
+ if len (conditions ) <= 1 :
134
+ condition_name = conditions .pop ()
135
+ codedeploy_application_resource .set_resource_attribute ("Condition" , condition_name )
107
136
return codedeploy_application_resource
108
137
109
- def _codedeploy_iam_role (self ):
138
+ def get_codedeploy_iam_role (self ):
110
139
iam_role = IAMRole (CODE_DEPLOY_SERVICE_ROLE_LOGICAL_ID )
111
140
iam_role .AssumeRolePolicyDocument = {
112
141
"Version" : "2012-10-17" ,
@@ -130,6 +159,12 @@ def _codedeploy_iam_role(self):
130
159
ArnGenerator .generate_aws_managed_policy_arn ("service-role/AWSCodeDeployRoleForLambda" )
131
160
]
132
161
162
+ if self .needs_resource_condition ():
163
+ conditions = self .get_all_deployment_conditions ()
164
+ condition_name = CODE_DEPLOY_CONDITION_NAME
165
+ if len (conditions ) <= 1 :
166
+ condition_name = conditions .pop ()
167
+ iam_role .set_resource_attribute ("Condition" , condition_name )
133
168
return iam_role
134
169
135
170
def deployment_group (self , function_logical_id ):
@@ -147,7 +182,7 @@ def deployment_group(self, function_logical_id):
147
182
except ValueError as e :
148
183
raise InvalidResourceException (function_logical_id , str (e ))
149
184
150
- deployment_group .ApplicationName = self . codedeploy_application . get_runtime_attr ( "name" )
185
+ deployment_group .ApplicationName = ref ( CODEDEPLOY_APPLICATION_LOGICAL_ID )
151
186
deployment_group .AutoRollbackConfiguration = {
152
187
"Enabled" : True ,
153
188
"Events" : ["DEPLOYMENT_FAILURE" , "DEPLOYMENT_STOP_ON_ALARM" , "DEPLOYMENT_STOP_ON_REQUEST" ],
@@ -159,7 +194,7 @@ def deployment_group(self, function_logical_id):
159
194
160
195
deployment_group .DeploymentStyle = {"DeploymentType" : "BLUE_GREEN" , "DeploymentOption" : "WITH_TRAFFIC_CONTROL" }
161
196
162
- deployment_group .ServiceRoleArn = self . codedeploy_iam_role . get_runtime_attr ( "arn " )
197
+ deployment_group .ServiceRoleArn = fnGetAtt ( CODE_DEPLOY_SERVICE_ROLE_LOGICAL_ID , "Arn " )
163
198
if deployment_preference .role :
164
199
deployment_group .ServiceRoleArn = deployment_preference .role
165
200
@@ -253,7 +288,7 @@ def update_policy(self, function_logical_id):
253
288
deployment_preference = self .get (function_logical_id )
254
289
255
290
return UpdatePolicy (
256
- self . codedeploy_application . get_runtime_attr ( "name" ),
291
+ ref ( CODEDEPLOY_APPLICATION_LOGICAL_ID ),
257
292
self .deployment_group (function_logical_id ).get_runtime_attr ("name" ),
258
293
deployment_preference .pre_traffic_hook ,
259
294
deployment_preference .post_traffic_hook ,
0 commit comments