---
#--------------------------------------------------------------------------------
#   Copyright Amazon.com Inc. or its affiliates. All Rights Reserved.
#
#  Licensed under the Apache License, Version 2.0 (the "License"). You may not use this file except in compliance
#  with the License. A copy of the License is located at
#
#      http://www.apache.org/licenses/LICENSE-2.0
#
#  or in the 'license' file accompanying this file. This file is distributed on an 'AS IS' BASIS, WITHOUT WARRANTIES
#  OR CONDITIONS OF ANY KIND, express or implied. See the License for the specific language governing permissions
#  and limitations under the License.
#---------------------------------------------------------------------------------
AWSTemplateFormatVersion: "2010-09-09"
Transform: AWS::Serverless-2016-10-31
Description: CDF (AWS Connected Device Framework)

Parameters:
  Environment:
    Description: Name of environment.  Used to name the created resources.
    Type: String
    MinLength: 1
  ArtifactsBucket:
    Description: Name of the S3 Bucket to store Device artifacts
    Type: String
  ArtifactsConfigPrefix:
    Description: Key prefix within bucket where config artifacts are uploaded to.
    Type: String
    Default: "config/"
  KmsKeyId:
    Description: The KMS key ID used to encrypt SSM parameters. If not provided, one will be created.
    Type: String
  TemplateSnippetS3UriBase:
    Description: |
      S3 uri of directory where template snippets are stored for the account.
    Type: String
    MinLength: 1
  AuthType:
    Description: Authorization type to apply to the API gateway endpoints
    Type: String
    Default: None
    AllowedValues:
      - None
      - Private
      - Cognito
      - LambdaRequest
      - LambdaToken
      - ApiKey
      - IAM
    MinLength: 1
  ApiGatewayDefinitionTemplate:
    Description: |
      Name of the API Gateway Cloudformation definition along with the authorization method to use.  Use one of the provided
      templates to implement no auth, private, api key, lambda request, lamdba token, or Cognito auth, or modify one to meet your own
      authentization requirements.  The template must exist within the provided TemplateSnippetS3UriBase location.
    Default: "cfn-apiGateway-noAuth.yaml"
    Type: String
    MinLength: 1
  ExistingEventBusArn:
    Description: Arn of an existing eventbus to use instead of creating one.
    Type: String
    Default: ""
  ExistingVpcId:
    Description: |
      ID of an existing VPC to deploy CDF (if using AuthType = 'Private') and/or AssetLibrary (if AssetLibraryMode = 'full') into.
      A new VPC will be created if not provided.
    Type: String
    Default: "N/A"
  ExistingCDFSecurityGroupId:
    Description: |
      ID of an existing security group to deploy CDF and/or AssetLibrary into if an existing VPC is to be used.
      A new security group will be created if not provided.
    Type: String
    Default: "N/A"
  ExistingPrivateSubnetIds:
    Description: |
      ID of existing private subnetIds to deploy CDF and/or AssetLibrary into if an existing VPC is to be used.
      New private subnets will be created if not provided.
    Type: String
    Default: "N/A"
  ExistingPublicSubnetIds:
    Description: |
      ID of existing public subnetIds to deploy CDF and/or AssetLibrary into if an existing VPC is to be used.
      New public subnets will be created if not provided.
    Type: String
    Default: "N/A"
  ExistingPrivateRouteTableIds:
    Description: |
      ID of existing private route tables to deploy AssetLibrary into if an existing VPC is to be used.
      New private route tables will be created if not provided.
    Type: String
    Default: "N/A"
  ExistingPrivateApiGatewayVPCEndpoint:
    Description: |
      ID of existing VPC endpoint to deploy CDF and/or AssetLibrary into if an existing VPC is to be used.
      New VPC endpoint will be created if not provided.
    Type: String
    Default: "N/A"
  CognitoUserPoolArn:
    Description: Cognito user pool arn.  Only required if AuthType is set to 'Cognito'.
    Type: String
    Default: "N/A"
  AuthorizerFunctionArn:
    Description: Lambda authorizer function arn.  Only required if AuthType is set to 'LambdaRequest' or 'LambdaToken'.
    Type: String
    Default: "N/A"
  BastionKeyPairName:
    Description: Bastion Key Pair name
    Type: String
  BastionRemoteAccessCIDR:
    AllowedPattern: "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])(\\/([0-9]|[1-2][0-9]|3[0-2]))$"
    ConstraintDescription: CIDR block parameter must be in the form x.x.x.x/x
    Description: Allowed CIDR block for external SSH access to the bastions
    Type: String

  IncludeDevicePatcher:
    Description: If true, the Device Patcher service will be deployed.
    Type: String
    Default: "true"
    AllowedValues:
      - "true"
      - "false"
    MinLength: 1

  IncludeGreengrass2:
    Description: If true, the Greengrass2 Provisioning and Installer Configs Generator service will be deployed.
    Type: String
    Default: "true"
    AllowedValues:
      - "true"
      - "false"
    MinLength: 1

  IncludeAssetLibrary:
    Description: If true, the Asset Library service will be deployed.
    Type: String
    Default: "true"
    AllowedValues:
      - "true"
      - "false"
    MinLength: 1
  AssetLibraryMode:
    Description: Run in 'lite' mode which includes device registry functionality only, or 'full' mode which augments the device registry with a graph based datastore.
    Type: String
    Default: "full"
    AllowedValues:
      - "full"
      - "lite"
    MinLength: 1
  IncludeProvisioning:
    Description: If true, the Provisioning service will be deployed.
    Type: String
    Default: "true"
    AllowedValues:
      - "true"
      - "false"
    MinLength: 1
  IncludeCommands:
    Description: If true, the Commands service will be deployed.
    Type: String
    Default: "true"
    AllowedValues:
      - "true"
      - "false"
    MinLength: 1
  IncludeDeviceMonitoring:
    Description: If true, the Device Monitoring service will be deployed.
    Type: String
    Default: "true"
    AllowedValues:
      - "true"
      - "false"
    MinLength: 1
  IncludeEventsProcessor:
    Description: If true, the Event Processor service will be deployed.
    Type: String
    Default: "true"
    AllowedValues:
      - "true"
      - "false"
    MinLength: 1
  IncludeEventsAlerts:
    Description: If true, the Event Alerts service will be deployed.
    Type: String
    Default: "true"
    AllowedValues:
      - "true"
      - "false"
    MinLength: 1
  IncludeAssetLibraryHistory:
    Description: If true, the Asset Library History service will be deployed.
    Type: String
    Default: "true"
    AllowedValues:
      - "true"
      - "false"
    MinLength: 1
  IncludeBulkCerts:
    Description: If true, the Bulk Certs service will be deployed.
    Type: String
    Default: "true"
    AllowedValues:
      - "true"
      - "false"
    MinLength: 1
  IncludeCertificateActivator:
    Description: If true, the CertificateActivator service will be deployed.
    Type: String
    Default: "true"
    AllowedValues:
      - "true"
      - "false"
    MinLength: 1
  IncludeCertificateVendor:
    Description: If true, the CertificateVendor service will be deployed.
    Type: String
    Default: "true"
    AllowedValues:
      - "true"
      - "false"
    MinLength: 1
  IncludeSimulationManager:
    Description: If true, then Simulation Manager will be deployed.
    Type: String
    Default: "true"
    AllowedValues:
      - "true"
      - "false"
  IncludeSimulationLauncher:
    Description: If true, then Simulation Launcher will be deployed.
    Type: String
    Default: "true"
    AllowedValues:
      - "true"
      - "false"
    MinLength: 1
  IncludeAssetLibraryExport:
    Description: If true, then Asset Library Exporter will be deployed.
    Type: String
    Default: "true"
    AllowedValues:
      - "true"
      - "false"
    MinLength: 1
  JMeterRepoName:
    Description: JMeter repository Name for the simulation launcher docker image.
    Type: String
    Default: "N/A"
  EnableApiGatewayAccessLogs:
    Description: Enables API gateway Access Logging, defaults to false if not specified.
    Type: String
    Default: "false"
    AllowedValues:
      - "true"
      - "false"
    MinLength: 1
  Greengrass2ProvisioningAppConfigOverride:
    Description: Greengrass2 Provisioning Application Configuration
    Type: String
    Default: ""
  DevicePatcherAppConfigOverride:
    Description: Device Patcher Application Configuration
    Type: String
    Default: ""
  Greengrass2InstallerConfigsGeneratorAppConfigOverride:
    Description: Greengrass2 Installer Configs Generator Application Configuration
    Type: String
    Default: ""
  AssetLibraryAppConfigOverride:
    Description: Asset Library Application Configuration AssetLibrary Application
    Type: String
    Default: ""
  AssetLibraryExportAppConfigOverride:
    Description: Asset Library Export Application Configuration AssetLibrary Application
    Type: String
    Default: ""
  ProvisioningAppConfigOverride:
    Description: Provisioning Application Configuration AssetLibrary Application
    Type: String
    Default: ""
  AssetLibraryHistoryAppConfigOverride:
    Description: Asset Library History Application Configuration AssetLibrary Application
    Type: String
    Default: ""
  CommandsAppConfigOverride:
    Description: Asset Library Application Configuration AssetLibrary Application
    Type: String
    Default: ""
  DeviceMonitoringAppConfigOverride:
    Description: Device Monitoring Application Configuration AssetLibrary Application
    Type: String
    Default: ""
  BulkCertsAppConfigOverride:
    Description: Bulk Certificates Application Configuration AssetLibrary Application
    Type: String
    Default: ""
  SimulationManagerAppConfigOverride:
    Description: Simulation Manager Application Configuration AssetLibrary Application
    Type: String
    Default: ""
  SimulationLauncherAppConfigOverride:
    Description: Simulation Launcher Application Configuration AssetLibrary Application
    Type: String
    Default: ""
  CertificateActivatorAppConfigOverride:
    Description: Certificate Activator Application Configuration AssetLibrary Application
    Type: String
    Default: ""
  CertificateVendorAppConfigOverride:
    Description: Certitificate Vendor Application Configuration AssetLibrary Application
    Type: String
    Default: ""
  EventsProcessorAppConfigOverride:
    Description: Event Processor Application Configuration AssetLibrary Application
    Type: String
    Default: ""
  EventsAlertsAppConfigOverride:
    Description: Event Alerts Vendor Application Configuration AssetLibrary Application
    Type: String
    Default: ""
  AssetLibraryExportETLMaxConcurrency:
    Description: Asset Library Export ETL Workflow Max Concurrency
    Type: String
    Default: 10
  NeptuneSnapshotIdentifier:
    Type: String
    Description: Specifies the identifier for an existing DB cluster snapshot to restore. Refer to Neptune documentation on its use.
    Default: ""
  NeptuneDbInstanceType:
    Description: >
      Neptune DB instance type. The list of available instance types for your region can be found here: 
      https://aws.amazon.com/neptune/pricing/
    Type: String
    AllowedPattern: "^db\\.[tr]\\d+[a-z0-9]*\\.[a-z0-9]*$"
    ConstraintDescription: Must be a valid Neptune instance type.

Conditions:
  DeployAssetLibrary: !Equals [!Ref IncludeAssetLibrary, "true"]
  DeployAssetLibraryFull:
    !And [
      !Condition DeployAssetLibrary,
      !Equals [!Ref AssetLibraryMode, "full"],
    ]
  DeployAssetLibraryExport:
    !And [
      !Condition DeployAssetLibrary,
      !Equals [!Ref IncludeAssetLibraryExport, "true"],
    ]
  DeployProvisioning: !Equals [!Ref IncludeProvisioning, "true"]
  DeployCommands:
    !And [!Condition DeployAssetLibrary, !Equals [!Ref IncludeCommands, "true"]]
  DeployEventsProcessor: !Equals [!Ref IncludeEventsProcessor, "true"]
  DeployAssetLibraryHistory:
    !And [
      !Condition DeployAssetLibrary,
      !Equals [!Ref IncludeAssetLibraryHistory, "true"],
    ]
  DeployBulkCerts: !Equals [!Ref IncludeBulkCerts, "true"]
  DeploySimulationManager: !Equals [!Ref IncludeSimulationManager, "true"]
  DeployGreengrass2: !Equals [!Ref IncludeGreengrass2, "true"]
  DeployDevicePatcher: !Equals [!Ref IncludeDevicePatcher, "true"]
  UsingVPCForAuth: !Equals [!Ref AuthType, "Private"]
  UsingVPCForAssetLibrary:
    !Or [!Condition UsingVPCForAuth, !Condition DeployAssetLibraryFull]

Resources:
  Shared:
    Type: AWS::CloudFormation::Stack
    Properties:
      TemplateURL: ./cfn-cdf-core-shared.yaml
      Parameters:
        Environment: !Ref Environment
        ArtifactsBucket: !Ref ArtifactsBucket
        KmsKeyId: !Ref KmsKeyId
        AuthType: !Ref AuthType
        ExistingEventBusArn: !Ref ExistingEventBusArn
        ExistingVpcId: !Ref ExistingVpcId
        ExistingCDFSecurityGroupId: !Ref ExistingCDFSecurityGroupId
        ExistingPrivateSubnetIds: !Ref ExistingPrivateSubnetIds
        ExistingPublicSubnetIds: !Ref ExistingPublicSubnetIds
        ExistingPrivateRouteTableIds: !Ref ExistingPrivateRouteTableIds
        ExistingPrivateApiGatewayVPCEndpoint: !Ref ExistingPrivateApiGatewayVPCEndpoint
        IncludeAssetLibrary: !Ref IncludeAssetLibrary
        AssetLibraryMode: !Ref AssetLibraryMode
      TimeoutInMinutes: 30

  ServicesA:
    Type: AWS::CloudFormation::Stack
    Properties:
      TemplateURL: ./cfn-cdf-core-services-A.yaml
      Parameters:
        EventBusArn: !GetAtt Shared.Outputs.EventBusArn
        Environment: !Ref Environment
        ArtifactsBucket: !Ref ArtifactsBucket
        KmsKeyId: !GetAtt Shared.Outputs.KmsKeyId
        TemplateSnippetS3UriBase: !Ref TemplateSnippetS3UriBase
        AuthType: !Ref AuthType
        ApiGatewayDefinitionTemplate: !Ref ApiGatewayDefinitionTemplate
        CognitoUserPoolArn: !Ref CognitoUserPoolArn
        AuthorizerFunctionArn: !Ref AuthorizerFunctionArn
        BastionKeyPairName: !Ref BastionKeyPairName
        BastionRemoteAccessCIDR: !Ref BastionRemoteAccessCIDR
        PublicSubNetIds:
          !If [
            UsingVPCForAssetLibrary,
            !GetAtt Shared.Outputs.PublicSubnetIds,
            "",
          ]
        IncludeGreengrass2: !Ref IncludeGreengrass2
        IncludeDevicePatcher: !Ref IncludeDevicePatcher
        IncludeAssetLibrary: !Ref IncludeAssetLibrary
        AssetLibraryMode: !Ref AssetLibraryMode
        VpcId: !If [UsingVPCForAssetLibrary, !GetAtt Shared.Outputs.VpcId, ""]
        CDFSecurityGroupId:
          !If [
            UsingVPCForAssetLibrary,
            !GetAtt Shared.Outputs.CDFSecurityGroupId,
            "",
          ]
        PrivateSubNetIds:
          !If [
            UsingVPCForAssetLibrary,
            !GetAtt Shared.Outputs.PrivateSubnetIds,
            "",
          ]
        PrivateRouteTableIds:
          !If [
            UsingVPCForAssetLibrary,
            !GetAtt Shared.Outputs.PrivateRouteTableIds,
            "",
          ]
        PrivateApiGatewayVPCEndpoint:
          !If [
            UsingVPCForAssetLibrary,
            !GetAtt Shared.Outputs.PrivateApiGatewayVPCEndpoint,
            "",
          ]
        AssetLibraryExportETLMaxConcurrency: !Ref AssetLibraryExportETLMaxConcurrency
        IncludeProvisioning: !Ref IncludeProvisioning
        OpenSslLambdaLayerArn: !GetAtt Shared.Outputs.OpenSslLambdaLayerArn
        IncludeCommands: !Ref IncludeCommands
        IncludeDeviceMonitoring: !Ref IncludeDeviceMonitoring
        IncludeEventProcessor: !Ref IncludeEventsProcessor
        IncludeEventAlerts: !Ref IncludeEventsAlerts
        IncludeAssetLibraryHistory: !Ref IncludeAssetLibraryHistory
        IncludeBulkCerts: !Ref IncludeBulkCerts
        IncludeCertificateActivator: !Ref IncludeCertificateActivator
        IncludeCertificateVendor: !Ref IncludeCertificateVendor
        IncludeAssetLibraryExport: !Ref IncludeAssetLibraryExport
        CustomResourceLambdaArn: !GetAtt Shared.Outputs.CustomResourceLambdaArn
        CustomResourceVPCLambdaArn: !GetAtt Shared.Outputs.CustomResourceVPCLambdaArn
        EnableApiGatewayAccessLogs: !Ref EnableApiGatewayAccessLogs
        Greengrass2ProvisioningAppConfigOverride: !Ref Greengrass2ProvisioningAppConfigOverride
        Greengrass2InstallerConfigsGeneratorAppConfigOverride: !Ref Greengrass2InstallerConfigsGeneratorAppConfigOverride
        DevicePatcherAppConfigOverride: !Ref DevicePatcherAppConfigOverride
        CertificateActivatorAppConfigOverride: !Ref CertificateActivatorAppConfigOverride
        CertificateVendorAppConfigOverride: !Ref CertificateVendorAppConfigOverride
        EventProcessorAppConfigOverride: !Ref EventsProcessorAppConfigOverride
        EventAlertsAppConfigOverride: !Ref EventsAlertsAppConfigOverride
        AssetLibraryAppConfigOverride: !Ref AssetLibraryAppConfigOverride
        AssetLibraryExportAppConfigOverride: !Ref AssetLibraryExportAppConfigOverride
        ProvisioningAppConfigOverride: !Ref ProvisioningAppConfigOverride
        AssetLibraryHistoryAppConfigOverride: !Ref AssetLibraryHistoryAppConfigOverride
        CommandsAppConfigOverride: !Ref CommandsAppConfigOverride
        DeviceMonitoringAppConfigOverride: !Ref DeviceMonitoringAppConfigOverride
        BulkCertsAppConfigOverride: !Ref BulkCertsAppConfigOverride
        NeptuneSnapshotIdentifier: !Ref NeptuneSnapshotIdentifier
        NeptuneDbInstanceType: !Ref NeptuneDbInstanceType
      TimeoutInMinutes: 120
    DependsOn:
      - Shared

  ServicesB:
    Type: AWS::CloudFormation::Stack
    Properties:
      TemplateURL: ./cfn-cdf-core-services-B.yaml
      Parameters:
        Environment: !Ref Environment
        ArtifactsBucket: !Ref ArtifactsBucket
        ArtifactsConfigPrefix: !Ref ArtifactsConfigPrefix
        TemplateSnippetS3UriBase: !Ref TemplateSnippetS3UriBase
        AuthType: !Ref AuthType
        ApiGatewayDefinitionTemplate: !Ref ApiGatewayDefinitionTemplate
        CognitoUserPoolArn: !Ref CognitoUserPoolArn
        AuthorizerFunctionArn: !Ref AuthorizerFunctionArn
        PublicSubNetIds:
          !If [
            UsingVPCForAssetLibrary,
            !GetAtt Shared.Outputs.PublicSubnetIds,
            "",
          ]
        VpcId: !If [UsingVPCForAssetLibrary, !GetAtt Shared.Outputs.VpcId, ""]
        CDFSecurityGroupId:
          !If [
            UsingVPCForAssetLibrary,
            !GetAtt Shared.Outputs.CDFSecurityGroupId,
            "",
          ]
        PrivateSubNetIds:
          !If [
            UsingVPCForAssetLibrary,
            !GetAtt Shared.Outputs.PrivateSubnetIds,
            "",
          ]
        PrivateApiGatewayVPCEndpoint:
          !If [
            UsingVPCForAssetLibrary,
            !GetAtt Shared.Outputs.PrivateApiGatewayVPCEndpoint,
            "",
          ]
        IncludeSimulationManager: !Ref IncludeSimulationManager
        IncludeSimulationLauncher: !Ref IncludeSimulationLauncher
        CustomResourceLambdaArn: !GetAtt Shared.Outputs.CustomResourceLambdaArn
        AssetLibraryFunctionName: !GetAtt ServicesA.Outputs.AssetLibraryRestApiFunctionName
        KmsKeyId: !GetAtt Shared.Outputs.KmsKeyId
        JMeterRepoName: !Ref JMeterRepoName
        EnableApiGatewayAccessLogs: !Ref EnableApiGatewayAccessLogs
        SimulationManagerAppConfigOverride: !Ref SimulationManagerAppConfigOverride
        SimulationLauncherAppConfigOverride: !Ref SimulationLauncherAppConfigOverride
      TimeoutInMinutes: 120
    DependsOn:
      - Shared

Outputs:
  KmsKeyId:
    Description: KMS Key ID
    Value: !GetAtt Shared.Outputs.KmsKeyId

  AssetLibraryRestApiFunctionName:
    Condition: DeployAssetLibrary
    Description: Asset library REST API lambda function name
    Value: !GetAtt ServicesA.Outputs.AssetLibraryRestApiFunctionName
  AssetLibraryApiGatewayUrl:
    Condition: DeployAssetLibrary
    Description: Asset Library REST API URL
    Value: !GetAtt ServicesA.Outputs.AssetLibraryApiGatewayUrl
  AssetLibraryApiGatewayHost:
    Condition: DeployAssetLibrary
    Description: Asset Library REST API host
    Value: !GetAtt ServicesA.Outputs.AssetLibraryApiGatewayHost

  ProvisioningRestApiFunctionName:
    Condition: DeployProvisioning
    Description: Provisioning REST API lambda function name
    Value: !GetAtt ServicesA.Outputs.ProvisioningRestApiFunctionName
  ProvisioningApiGatewayUrl:
    Condition: DeployProvisioning
    Description: Provisioning REST API URL
    Value: !GetAtt ServicesA.Outputs.ProvisioningApiGatewayUrl
  ProvisioningApiGatewayHost:
    Condition: DeployProvisioning
    Description: Provisioning REST API host
    Value: !GetAtt ServicesA.Outputs.ProvisioningApiGatewayHost

  CommandsRestApiFunctionName:
    Condition: DeployCommands
    Description: Commands REST API lambda function name
    Value: !GetAtt ServicesA.Outputs.CommandsRestApiFunctionName
  CommandsApiGatewayUrl:
    Condition: DeployCommands
    Description: Commands REST API URL
    Value: !GetAtt ServicesA.Outputs.CommandsApiGatewayUrl
  CommandsApiGatewayHost:
    Condition: DeployCommands
    Description: Commands REST API host
    Value: !GetAtt ServicesA.Outputs.CommandsApiGatewayHost

  EventsProcessorRestApiFunctionName:
    Condition: DeployEventsProcessor
    Description: Events Processor REST API lambda function name
    Value: !GetAtt ServicesA.Outputs.EventsProcessorRestApiFunctionName
  EventsProcessorApiGatewayUrl:
    Condition: DeployEventsProcessor
    Description: Events Processor REST API URL
    Value: !GetAtt ServicesA.Outputs.EventsProcessorApiGatewayUrl
  EventsProcessorApiGatewayHost:
    Condition: DeployEventsProcessor
    Description: Events Processor REST API host
    Value: !GetAtt ServicesA.Outputs.EventsProcessorApiGatewayHost

  AssetLibraryHistoryRestApiFunctionName:
    Condition: DeployAssetLibraryHistory
    Description: AssetLibraryHistory REST API lambda function name
    Value: !GetAtt ServicesA.Outputs.AssetLibraryHistoryRestApiFunctionName
  AssetLibraryHistoryApiGatewayUrl:
    Condition: DeployAssetLibraryHistory
    Description: AssetLibraryHistory REST API URL
    Value: !GetAtt ServicesA.Outputs.AssetLibraryHistoryApiGatewayUrl
  AssetLibraryHistoryApiGatewayHost:
    Condition: DeployAssetLibraryHistory
    Description: AssetLibraryHistory REST API host
    Value: !GetAtt ServicesA.Outputs.AssetLibraryHistoryApiGatewayHost

  BulkCertsRestApiFunctionName:
    Condition: DeployBulkCerts
    Description: Bulk Certs REST API lambda function name
    Value: !GetAtt ServicesA.Outputs.BulkCertsRestApiFunctionName
  BulkCertstApiGatewayUrl:
    Condition: DeployBulkCerts
    Description: Bulk Certs REST API URL
    Value: !GetAtt ServicesA.Outputs.BulkCertstApiGatewayUrl
  BulkCertsApiGatewayHost:
    Condition: DeployBulkCerts
    Description: Bulk Certs REST API host
    Value: !GetAtt ServicesA.Outputs.BulkCertsApiGatewayHost

  DevicePatcherRestApiFunctionName:
    Condition: DeployDevicePatcher
    Description: Device Patcher REST API lambda function name
    Value: !GetAtt ServicesA.Outputs.DevicePatcherRestApiFunctionName
  DevicePatcherApiGatewayUrl:
    Condition: DeployDevicePatcher
    Description: Device Patcher REST API URL
    Value: !GetAtt ServicesA.Outputs.DevicePatcherApiGatewayUrl
  Greengrass2ProvisioningRestApiFunctionName:
    Condition: DeployGreengrass2
    Description: Device Patcher REST API lambda function name
    Value: !GetAtt ServicesA.Outputs.Greengrass2ProvisioningRestApiFunctionName
  Greengrass2ProvisioningApiGatewayUrl:
    Condition: DeployGreengrass2
    Description: Device Patcher REST API URL
    Value: !GetAtt ServicesA.Outputs.Greengrass2ProvisioningApiGatewayUrl

  SimulationManagerRestApiFunctionName:
    Condition: DeploySimulationManager
    Description: SimulationManager REST API lambda function name
    Value: !GetAtt ServicesB.Outputs.SimulationManagerRestApiFunctionName
  SimulationManagerApiGatewayUrl:
    Condition: DeploySimulationManager
    Description: SimulationManager REST API URL
    Value: !GetAtt ServicesB.Outputs.SimulationManagerApiGatewayUrl
  SimulationManagerApiGatewayHost:
    Condition: DeploySimulationManager
    Description: SimulationManager REST API host
    Value: !GetAtt ServicesB.Outputs.SimulationManagerApiGatewayHost

  CDFVpcId:
    Description: CDF VPC ID
    Value: !GetAtt Shared.Outputs.VpcId
  CDFSecurityGroupId:
    Description: CDF VPC Security Groups
    Value: !GetAtt Shared.Outputs.CDFSecurityGroupId
  CDFPrivateSubnetIds:
    Description: CDF VPC Private Subnets
    Value: !GetAtt Shared.Outputs.PrivateSubnetIds
  CDFPublicSubnetIds:
    Description: CDF VPC Public Subnets
    Value: !GetAtt Shared.Outputs.PublicSubnetIds

  AssetLibraryExportETLLambdaFunctionName:
    Condition: DeployAssetLibraryExport
    Description: AssetLibrary Export ETL Lambda Function name
    Value: !GetAtt ServicesA.Outputs.AssetLibraryExportETLLambdaFunctionName
  AssetLibraryExportBatchLambdaFunctionName:
    Condition: DeployAssetLibraryExport
    Description: AssetLibrary Export Batch Lambda Function name
    Value: !GetAtt ServicesA.Outputs.AssetLibraryExportBatchLambdaFunctionName
  AssetLibraryExportExportCompletionSnsTopic:
    Condition: DeployAssetLibraryExport
    Description: Export Completion SNS Topic
    Value: !GetAtt ServicesA.Outputs.AssetLibraryExportExportCompletionSnsTopic
