2828
2929class OrganizationStack (Stack ):
3030 """
31- Class to create the infrastructure of the AWS Organizations.
31+ Class to create the infrastructure for AWS Organizations.
3232 """
3333
3434 def __init__ (
3535 self , scope : Construct , construct_id : str , deployment_environment : str , ** kwargs
3636 ) -> None :
37+ """
38+ :param scope (Construct): Parent of this stack, usually an ``App`` or a ``Stage``, but could be any construct.
39+ :param construct_id (str): The construct ID of this stack.
40+ :param main_resources_name (str): The main solution name being deployed.
41+ :param deployment_environment (str): Value that represents the deployment environment. For example: "dev" or "prod".
42+ """
3743 super ().__init__ (scope , construct_id , ** kwargs )
3844
3945 self .construct_id = construct_id
4046 self .deployment_environment = deployment_environment
4147
42- # Organization creation, services configuration and SCPs
48+ # AWS Organization creation, services configuration and SCPs
4349 self .create_root_organization ()
4450 self .configure_organization_services ()
4551 self .configure_service_control_policies ()
@@ -48,6 +54,19 @@ def __init__(
4854 self .create_ou_sandbox ()
4955 self .create_accounts_inside_ou_sandbox ()
5056
57+ # Create "infrastructure" OU with inner OUs and accounts inside
58+ self .create_ou_infrastructure ()
59+ self .create_accounts_inside_ou_infrastructure ()
60+
61+ # Create "workloads" OU with inner OUs and accounts inside
62+ self .create_ou_workloads ()
63+ self .create_ou_finance ()
64+ self .create_accounts_inside_ou_finance ()
65+
66+ # Create "policy_staging_tests" OU with inner OUs and accounts inside
67+ self .create_ou_policy_staging_tests ()
68+ self .create_accounts_inside_ou_policy_staging_tests ()
69+
5170 # !IMPORTANT: this is mandatory for adding CDK dependencies for each account
5271 self .add_cdk_accounts_dependencies () # DO NOT REMOVE!
5372
@@ -60,7 +79,7 @@ def create_root_organization(self):
6079 """
6180 self .organization = Organization (
6281 self ,
63- id = "RootOrganization" ,
82+ "RootOrganization" ,
6483 feature_set = FeatureSet .ALL ,
6584 )
6685
@@ -107,7 +126,7 @@ def configure_service_control_policies(self):
107126 # SCP for preventing accounts of leaving organization
108127 self .policy_deny_leave_org = Policy (
109128 self ,
110- id = "PolicyDenyLeave" ,
129+ "PolicyDenyLeave" ,
111130 content = json .dumps (scp_prevent_leaving_org ),
112131 policy_name = "PreventLeavingOrganization" ,
113132 policy_type = PolicyType .SERVICE_CONTROL_POLICY ,
@@ -118,7 +137,7 @@ def configure_service_control_policies(self):
118137 # SCP for only allow access to specific regions in AWS (deny others)
119138 self .policy_allow_specific_regions = Policy (
120139 self ,
121- id = "PolicyAllowSpecificRegions" ,
140+ "PolicyAllowSpecificRegions" ,
122141 content = json .dumps (scp_allow_specific_regions ),
123142 policy_name = "AllowSpecificRegions" ,
124143 policy_type = PolicyType .SERVICE_CONTROL_POLICY ,
@@ -128,47 +147,196 @@ def configure_service_control_policies(self):
128147
129148 def create_ou_sandbox (self ):
130149 """
131- Method that creates inner Organizational Units (OUs) inside organization.
150+ Method that creates inner Organizational Units (OUs) inside the AWS
151+ Organization for "Sandbox".
132152 """
133153 self .top_level_ou_sandbox = OrganizationalUnit (
134154 self ,
135- id = "SandboxOU" ,
155+ "SandboxOU" ,
136156 parent = self .organization .root ,
137157 organizational_unit_name = "sandbox" ,
138158 )
139159
140160 def create_accounts_inside_ou_sandbox (self ):
141161 """
142- Method that creates AWS Accounts inside the required Organizational
143- Units (OUs) .
162+ Method that creates AWS Accounts inside the Organizational Units (OUs)
163+ for "Sandbox" .
144164 """
145165 self .account_sandbox_1 = Account (
146166 self ,
147- id = "SandboxAccount1" ,
167+ "SandboxAccount1" ,
148168 account_name = "san99tiago-sandbox-1" ,
149169 email = "san99tiagodemo+san99tiago-sandbox-1@gmail.com" ,
150170 parent = self .top_level_ou_sandbox ,
151171 role_name = "OrganizationAccountAccessRole" ,
152172 )
153173 self .account_sandbox_2 = Account (
154174 self ,
155- id = "SandboxAccount2" ,
175+ "SandboxAccount2" ,
156176 account_name = "san99tiago-sandbox-2" ,
157177 email = "san99tiagodemo+san99tiago-sandbox-2@gmail.com" ,
158178 parent = self .top_level_ou_sandbox ,
159179 role_name = "OrganizationAccountAccessRole" ,
160180 )
161181
182+ def create_ou_infrastructure (self ):
183+ """
184+ Method that creates inner Organizational Units (OUs) inside the AWS
185+ Organization for "Infrastructure".
186+ """
187+ self .top_level_ou_infrastructure = OrganizationalUnit (
188+ self ,
189+ "OUInfrastructure" ,
190+ parent = self .organization .root ,
191+ organizational_unit_name = "infrastructure" ,
192+ )
193+ self .ou_infrastructure_non_prod = OrganizationalUnit (
194+ self ,
195+ "OUInfrastructureNonProd" ,
196+ parent = self .top_level_ou_infrastructure ,
197+ organizational_unit_name = "non-prod" ,
198+ )
199+ self .ou_infrastructure_prod = OrganizationalUnit (
200+ self ,
201+ "OUInfrastructureProd" ,
202+ parent = self .top_level_ou_infrastructure ,
203+ organizational_unit_name = "prod" ,
204+ )
205+
206+ def create_accounts_inside_ou_infrastructure (self ):
207+ """
208+ Method that creates AWS Accounts inside the Organizational Units (OUs)
209+ for "Infrastructure".
210+ """
211+ self .account_shared_services_non_prod = Account (
212+ self ,
213+ "AccountSharedServicesNonProd" ,
214+ account_name = "shared-services-non-prod" ,
215+ email = "san99tiagodemo+shared-services-non-prod@gmail.com" ,
216+ parent = self .ou_infrastructure_non_prod ,
217+ role_name = "OrganizationAccountAccessRole" ,
218+ )
219+ self .account_shared_services_prod = Account (
220+ self ,
221+ "AccountSharedServicesProd" ,
222+ account_name = "shared-services-prod" ,
223+ email = "san99tiagodemo+shared-services-prod@gmail.com" ,
224+ parent = self .ou_infrastructure_prod ,
225+ role_name = "OrganizationAccountAccessRole" ,
226+ )
227+
228+ def create_ou_workloads (self ):
229+ """
230+ Method that creates inner Organizational Units (OUs) inside the AWS
231+ Organization for "Workloads".
232+ """
233+ self .top_level_ou_workloads = OrganizationalUnit (
234+ self ,
235+ "OUWorkloads" ,
236+ parent = self .organization .root ,
237+ organizational_unit_name = "workloads" ,
238+ )
239+
240+ def create_ou_finance (self ):
241+ """
242+ Method that creates inner Organizational Units (OUs) inside the AWS
243+ Organization for "Finance".
244+ """
245+ self .ou_finance = OrganizationalUnit (
246+ self ,
247+ "OUFinance" ,
248+ parent = self .top_level_ou_workloads ,
249+ organizational_unit_name = "finance" ,
250+ )
251+ self .ou_finance_non_prod = OrganizationalUnit (
252+ self ,
253+ "OUFinanceNonProd" ,
254+ parent = self .ou_finance ,
255+ organizational_unit_name = "non-prod" ,
256+ )
257+ self .ou_finance_prod = OrganizationalUnit (
258+ self ,
259+ "OUFinanceProd" ,
260+ parent = self .ou_finance ,
261+ organizational_unit_name = "prod" ,
262+ )
263+
264+ def create_accounts_inside_ou_finance (self ):
265+ """
266+ Method that creates AWS Accounts inside the Organizational Units (OUs)
267+ for "Finance".
268+ """
269+ self .account_finance_dev = Account (
270+ self ,
271+ "AccountFinanceDev" ,
272+ account_name = "finance-dev" ,
273+ email = "san99tiagodemo+finance-dev@gmail.com" ,
274+ parent = self .ou_finance_non_prod ,
275+ role_name = "OrganizationAccountAccessRole" ,
276+ )
277+ self .account_finance_qa = Account (
278+ self ,
279+ "AccountFinanceQA" ,
280+ account_name = "finance-qa" ,
281+ email = "san99tiagodemo+finance-qa@gmail.com" ,
282+ parent = self .ou_finance_non_prod ,
283+ role_name = "OrganizationAccountAccessRole" ,
284+ )
285+ self .account_finance_prod = Account (
286+ self ,
287+ "AccountFinanceProd" ,
288+ account_name = "finance-prod" ,
289+ email = "san99tiagodemo+finance-prod@gmail.com" ,
290+ parent = self .ou_finance_prod ,
291+ role_name = "OrganizationAccountAccessRole" ,
292+ )
293+
294+ def create_ou_policy_staging_tests (self ):
295+ """
296+ Method that creates inner Organizational Units (OUs) inside the AWS
297+ Organization for "PolicyStagingTests".
298+ """
299+ self .top_level_ou_policy_staging_tests = OrganizationalUnit (
300+ self ,
301+ "OUPolicyStagingTests" ,
302+ parent = self .organization .root ,
303+ organizational_unit_name = "policy-staging-tests" ,
304+ )
305+
306+ def create_accounts_inside_ou_policy_staging_tests (self ):
307+ """
308+ Method that creates AWS Accounts inside the Organizational Units (OUs)
309+ for "PolicyStagingTests".
310+ """
311+ self .account_policy_staging_tests = Account (
312+ self ,
313+ "AccountPolicyStagingTests" ,
314+ account_name = "policy-staging-tests" ,
315+ email = "san99tiagodemo+policy-staging-tests@gmail.com" ,
316+ parent = self .top_level_ou_policy_staging_tests ,
317+ role_name = "OrganizationAccountAccessRole" ,
318+ )
319+
162320 def add_cdk_accounts_dependencies (self ):
163321 """
164- ULTRA IMPORTANT METHOD to add CDK dependencies for the AWS Accounts that
165- are being created (to avoid 2 accounts creation simultaneously, which is
322+ IMPORTANT METHOD to add CDK dependencies for the AWS Accounts that are
323+ being created (to avoid 2 accounts creation simultaneously, which is
166324 not supported by AWS). This is because of AWS Organizations limitation.
167325 """
168326 # ! IMPORTANT: We MUST add these dependencies, as AWS Organizations only support
169327 # ... one account creation "IN_PROGRESS". We add CDK dependency to solve issue
170328 # ... and wait for the previous one to finish, to continue with the next...
171329 self .account_sandbox_2 .node .add_dependency (self .account_sandbox_1 )
330+ self .account_shared_services_non_prod .node .add_dependency (
331+ self .account_sandbox_2
332+ )
333+ self .account_shared_services_prod .node .add_dependency (
334+ self .account_shared_services_non_prod
335+ )
336+ self .account_finance_dev .node .add_dependency (self .account_shared_services_prod )
337+ self .account_finance_qa .node .add_dependency (self .account_finance_dev )
338+ self .account_finance_prod .node .add_dependency (self .account_finance_qa )
339+ self .account_policy_staging_tests .node .add_dependency (self .account_finance_prod )
172340
173341 def generate_cloudformation_outputs (self ):
174342 """
@@ -186,21 +354,21 @@ def generate_cloudformation_outputs(self):
186354 self ,
187355 "OrganizationId" ,
188356 value = self .organization .organization_id ,
189- description = "ID of the Organization" ,
357+ description = "ID of AWS Organization" ,
190358 )
191359
192360 CfnOutput (
193361 self ,
194362 "RootId" ,
195363 value = self .organization .root .identifier (),
196- description = "ID of the Root OU" ,
364+ description = "ID of AWS Organization Root OU" ,
197365 )
198366
199367 CfnOutput (
200368 self ,
201369 "ManagementAccountId" ,
202370 value = self .organization .management_account_id ,
203- description = "ID of the Management Account" ,
371+ description = "ID of Management Account" ,
204372 )
205373
206374 CfnOutput (
@@ -214,12 +382,54 @@ def generate_cloudformation_outputs(self):
214382 self ,
215383 "AccountSandbox1Id" ,
216384 value = self .account_sandbox_1 .account_id ,
217- description = "ID of the SandboxAccount1" ,
385+ description = "ID of SandboxAccount1 Account " ,
218386 )
219387
220388 CfnOutput (
221389 self ,
222390 "AccountSandbox2Id" ,
223391 value = self .account_sandbox_2 .account_id ,
224- description = "ID of the SandboxAccount2" ,
392+ description = "ID of SandboxAccount2 Account" ,
393+ )
394+
395+ CfnOutput (
396+ self ,
397+ "AccountSharedServicesNonProdId" ,
398+ value = self .account_shared_services_non_prod .account_id ,
399+ description = "ID of AccountSharedServicesNonProd Account" ,
400+ )
401+
402+ CfnOutput (
403+ self ,
404+ "AccountSharedServicesProdId" ,
405+ value = self .account_shared_services_prod .account_id ,
406+ description = "ID of AccountSharedServicesProd Account" ,
407+ )
408+
409+ CfnOutput (
410+ self ,
411+ "AccountFinanceDevId" ,
412+ value = self .account_finance_dev .account_id ,
413+ description = "ID of AccountFinanceDev Account" ,
414+ )
415+
416+ CfnOutput (
417+ self ,
418+ "AccountFinanceQAId" ,
419+ value = self .account_finance_qa .account_id ,
420+ description = "ID of AccountFinanceQA Account" ,
421+ )
422+
423+ CfnOutput (
424+ self ,
425+ "AccountFinanceProdId" ,
426+ value = self .account_finance_prod .account_id ,
427+ description = "ID of AccountFinanceProd Account" ,
428+ )
429+
430+ CfnOutput (
431+ self ,
432+ "AccountPolicyStagingTestsId" ,
433+ value = self .account_policy_staging_tests .account_id ,
434+ description = "ID of AccountPolicyStagingTests Account" ,
225435 )
0 commit comments