def iam_roles()

in installer/resources/src/cdk_construct.py [0:0]


    def iam_roles(self):
        """
        Configure IAM roles & policies for the various resources
        """
        # Specify if customers want to re-use existing IAM role for scheduler/compute nodes/spotfleet
        if user_specified_variables.scheduler_role_name:
            use_existing_roles = True
        else:
            use_existing_roles = False

        # Create IAM roles
        self.soca_resources["backup_role"] = iam.Role(self, 'BackupRole', description="IAM role to manage AWS Backup & Restore jobs", assumed_by=iam.ServicePrincipal(principals_suffix["backup"]))
        self.soca_resources["acm_certificate_lambda_role"] = iam.Role(self, 'ACMCertificateLambdaRole', description="IAM role assigned to the ACMCertificate Lambda function", assumed_by=iam.ServicePrincipal(principals_suffix["lambda"]))
        self.soca_resources["solution_metrics_lambda_role"] = iam.Role(self, 'SolutionMetricsLambdaRole', description="IAM role assigned to the SolutionMetrics Lambda function", assumed_by=iam.ServicePrincipal(principals_suffix["lambda"]))

        # Create Role for EFS Throughput Lambda function only when deploying a new EFS for /apps
        if not user_specified_variables.fs_apps_provider or user_specified_variables.fs_apps_provider == "efs":
            self.soca_resources["fs_apps_lambda_role"] = iam.Role(self, 'EFSAppsLambdaRole', description="IAM role assigned to the EFSApps Lambda function", assumed_by=iam.ServicePrincipal(principals_suffix["lambda"]))

        # CreateRole for GetESPrivateIPLambdaRole when creating a new ElasticSearch
        if not user_specified_variables.es_endpoint:
            self.soca_resources["get_es_private_ip_lambda_role"] = iam.Role(self, 'GetESPrivateIPLambdaRole', description="IAM role assigned to the EFSApps Lambda function", assumed_by=iam.ServicePrincipal(principals_suffix["lambda"]))

        if use_existing_roles is False:
            # Create Scheduler/ComputeNode/SpotFleet roles if not specified by the user
            self.soca_resources["scheduler_role"] = iam.Role(self, "SchedulerRole", description="IAM role assigned to the scheduler host", assumed_by=iam.CompositePrincipal(iam.ServicePrincipal(principals_suffix["ssm"]), iam.ServicePrincipal(principals_suffix["ec2"])))
            self.soca_resources["compute_node_role"] = iam.Role(self, "ComputeNodeRole", description="IAM role assigned to the compute nodes", assumed_by=iam.CompositePrincipal(iam.ServicePrincipal(principals_suffix["ssm"]), iam.ServicePrincipal(principals_suffix["ec2"])))
            self.soca_resources["spot_fleet_role"] = iam.Role(self, "SpotFleetRole", description="IAM role to manage SpotFleet requests", assumed_by=iam.ServicePrincipal(principals_suffix["spotfleet"]))
            self.soca_resources["spot_fleet_role"].add_managed_policy(iam.ManagedPolicy.from_aws_managed_policy_name("service-role/AmazonEC2SpotFleetTaggingRole"))
            self.soca_resources["compute_node_instance_profile"] = iam.CfnInstanceProfile(self, "ComputeNodeInstanceProfile", roles=[self.soca_resources["compute_node_role"].role_name])
        else:
            # Reference existing Scheduler/ComputeNode/SpotFleet roles
            self.soca_resources["scheduler_role"] = iam.Role.from_role_arn(self, "SchedulerRole", role_arn=user_specified_variables.scheduler_role_arn)
            self.soca_resources["compute_node_role"] = iam.Role.from_role_arn(self, "ComputeNodeRole", role_arn=user_specified_variables.compute_node_role_arn)
            self.soca_resources["spot_fleet_role"] = iam.Role.from_role_arn(self, "SpotFleetRole", role_arn=user_specified_variables.spotfleet_role_arn)
            self.soca_resources["compute_node_instance_profile"] = iam.CfnInstanceProfile(self, "ComputeNodeInstanceProfile", roles=[user_specified_variables.compute_node_role_name])

        # Add SSM Managed Policy
        self.soca_resources["scheduler_role"].add_managed_policy(iam.ManagedPolicy.from_aws_managed_policy_name("AmazonSSMManagedInstanceCore"))
        self.soca_resources["compute_node_role"].add_managed_policy(iam.ManagedPolicy.from_aws_managed_policy_name("AmazonSSMManagedInstanceCore"))

        # Generate IAM inline policies
        policy_substitutes = {"%%AWS_ACCOUNT_ID%%": core.Aws.ACCOUNT_ID,
                              "%%AWS_PARTITION%%": core.Aws.PARTITION,
                              "%%AWS_URL_SUFFIX%%": core.Aws.URL_SUFFIX,
                              "%%AWS_REGION%%": core.Aws.REGION,
                              "%%BUCKET%%": user_specified_variables.bucket,
                              "%%COMPUTE_NODE_ROLE_ARN%%": self.soca_resources["compute_node_role"].role_arn if not user_specified_variables.compute_node_role_arn else user_specified_variables.compute_node_role_arn,
                              "%%SCHEDULER_ROLE_ARN%%": self.soca_resources["scheduler_role"].role_arn if not user_specified_variables.scheduler_role_arn else user_specified_variables.scheduler_role_arn,
                              "%%SPOTFLEET_ROLE_ARN%%": self.soca_resources["spot_fleet_role"].role_arn if not user_specified_variables.spotfleet_role_arn else user_specified_variables.spotfleet_role_arn,
                              "%%VPC_ID%%": self.soca_resources["vpc"].vpc_id,
                              "%%CLUSTER_ID%%": user_specified_variables.cluster_id}

        policy_templates = {"ACMCertificateLambdaPolicy": {"template": "../policies/ACMCertificateLambda.json", "attach_to_role": "acm_certificate_lambda_role"},
                            "BackupPolicy": {"template": "../policies/Backup.json", "attach_to_role": "backup_role"},
                            "SolutionMetricsLambdaPolicy": {"template": "../policies/SolutionMetricsLambda.json", "attach_to_role": "solution_metrics_lambda_role"}}

        if not user_specified_variables.es_endpoint:
            policy_templates["GetESPrivateIPLambdaPolicy"] = {"template": "../policies/GetESPrivateIPLambda.json", "attach_to_role": "get_es_private_ip_lambda_role"}

        if use_existing_roles is False:
            policy_templates["ComputeNodePolicy"] = {"template": "../policies/ComputeNode.json", "attach_to_role": "compute_node_role"}
            policy_templates["SchedulerPolicy"] = {"template": "../policies/Scheduler.json", "attach_to_role": "scheduler_role"}
            policy_templates["SpotFleetPolicy"] = {"template": "../policies/SpotFleet.json", "attach_to_role": "spot_fleet_role"}
        else:
            # Append required policies if IAM specified by user have not been generated by SOCA
            if user_specified_variables.scheduler_role_from_previous_soca_deployment:
                policy_templates["SchedulerPolicyNewCluster"] = {"template": "../policies/SchedulerAppendToExistingRole.json", "attach_to_role": "scheduler_role"}
            else:
                policy_templates["SchedulerPolicyNewCluster"] = {"template": "../policies/Scheduler.json", "attach_to_role": "scheduler_role"}

            if not user_specified_variables.compute_node_role_from_previous_soca_deployment:
                policy_templates["ComputeNodePolicy"] = {"template": "../policies/ComputeNode.json", "attach_to_role": "compute_node_role"}

            if not user_specified_variables.spotfleet_role_from_previous_soca_deployment:
                policy_templates["SpotFleetPolicy"] = {"template": "../policies/SpotFleet.json", "attach_to_role": "spot_fleet_role"}

        if not user_specified_variables.fs_apps:
            policy_templates["EFSAppsLambdaPolicy"] = {"template": "../policies/EFSAppsLambda.json", "attach_to_role": "fs_apps_lambda_role"}

        # Create additional IAM Role/Policy if we use Active Directory. This role is used by ResetDsLambda
        if install_props.Config.directoryservice.provider == "activedirectory":
            self.soca_resources["reset_ds_password_lambda_role"] = iam.Role(self, 'ResetDsLambdaLambdaRole', assumed_by=iam.ServicePrincipal(principals_suffix["lambda"]))
            policy_templates["ResetDSPasswordPolicy"] = {"template": "../policies/ResetDSPassword.json", "attach_to_role": "reset_ds_password_lambda_role"}

        # Create all policies and attach them to their respective role
        for policy_name, policy_data in policy_templates.items():
            with open(policy_data["template"]) as json_file:
                policy_content = json_file.read()

            for k, v in policy_substitutes.items():
                policy_content = policy_content.replace(k, v)

            self.soca_resources[policy_data["attach_to_role"]].attach_inline_policy(iam.Policy(self, f"{user_specified_variables.cluster_id}-{policy_name}", document=iam.PolicyDocument.from_json(json.loads(policy_content))))