AWSTemplateFormatVersion: '2010-09-09'
Transform: AWS::Serverless-2016-10-31
Description: Tinqs CI Orchestrator — Lambda dispatch + EC2 Spot runners

Parameters:
  GiteaURL:
    Type: String
    Default: https://tinqs.com
  GiteaToken:
    Type: String
    NoEcho: true
  RunnerAMI:
    Type: AWS::EC2::Image::Id
    Description: Pre-baked AMI with Go, Node, Docker, AWS CLI, act_runner
  Subnet:
    Type: AWS::EC2::Subnet::Id
    Description: Public subnet for spot instances
  SecurityGroup:
    Type: AWS::EC2::SecurityGroup::Id
    Description: Security group for spot instances
  InstanceProfileArn:
    Type: String
    Description: IAM instance profile ARN for runners

Globals:
  Function:
    Runtime: provided.al2023
    Architectures: [x86_64]
    Timeout: 30
    MemorySize: 128

Resources:

  # --- API Gateway ---
  WebhookApi:
    Type: AWS::Serverless::Api
    Properties:
      Name: tinqs-ci-webhook
      StageName: prod

  # --- DynamoDB ---
  RunsTable:
    Type: AWS::DynamoDB::Table
    Properties:
      TableName: tinqs-ci-runs
      BillingMode: PAY_PER_REQUEST
      AttributeDefinitions:
        - AttributeName: repo
          AttributeType: S
        - AttributeName: run_id
          AttributeType: S
      KeySchema:
        - AttributeName: repo
          KeyType: HASH
        - AttributeName: run_id
          KeyType: RANGE
      TimeToLiveSpecification:
        AttributeName: ttl
        Enabled: true

  # --- Dispatcher Lambda ---
  DispatchFunction:
    Type: AWS::Serverless::Function
    Properties:
      FunctionName: tinqs-ci-dispatch
      Handler: bootstrap
      CodeUri: ../dispatch/
      Description: Receives webhook, starts Spot instances or invokes Lambda executor
      Timeout: 60
      MemorySize: 256
      Environment:
        Variables:
          GITEA_URL: !Ref GiteaURL
          GITEA_TOKEN: !Ref GiteaToken
          EXECUTOR_FUNCTION_NAME: !Ref ExecFunction
          RUNNER_AMI: !Ref RunnerAMI
          SUBNET: !Ref Subnet
          SECURITY_GROUP: !Ref SecurityGroup
          DDB_TABLE: !Ref RunsTable
          INSTANCE_PROFILE: !Ref InstanceProfileArn
      Policies:
        - LambdaInvokePolicy:
            FunctionName: !Ref ExecFunction
        - DynamoDBCrudPolicy:
            TableName: !Ref RunsTable
        - Version: '2012-10-17'
          Statement:
            - Effect: Allow
              Action:
                - ec2:RunInstances
                - ec2:TerminateInstances
                - ec2:DescribeInstances
                - ec2:CreateTags
              Resource: '*'
            - Effect: Allow
              Action: iam:PassRole
              Resource: !Ref InstanceProfileArn
      Events:
        Webhook:
          Type: Api
          Properties:
            RestApiId: !Ref WebhookApi
            Path: /webhook
            Method: POST

  # --- Executor Lambda (deploy-only jobs) ---
  ExecFunction:
    Type: AWS::Serverless::Function
    Properties:
      FunctionName: tinqs-ci-exec
      Handler: bootstrap
      CodeUri: ../exec/
      Description: Executes deploy-only workflow steps directly in Lambda
      Timeout: 900
      MemorySize: 2048
      EphemeralStorage:
        Size: 5120
      Environment:
        Variables:
          GITEA_URL: !Ref GiteaURL
          GITEA_TOKEN: !Ref GiteaToken
      Policies:
        - S3CrudPolicy:
            BucketName: tinqs-cli-releases
        - S3CrudPolicy:
            BucketName: arikigame.com
        - S3CrudPolicy:
            BucketName: docs.tinqs.com
        - Version: '2012-10-17'
          Statement:
            - Effect: Allow
              Action:
                - ecs:UpdateService
                - ecs:DescribeServices
              Resource: !Sub 'arn:aws:ecs:${AWS::Region}:${AWS::AccountId}:service/tinqs-git/*'
            - Effect: Allow
              Action:
                - cloudfront:CreateInvalidation
              Resource: '*'

  # --- Cleanup Cron (every 5 min) ---
  CleanupRule:
    Type: AWS::Events::Rule
    Properties:
      Name: tinqs-ci-cleanup
      ScheduleExpression: 'rate(5 minutes)'
      State: ENABLED
      Targets:
        - Id: cleanup
          Arn: !GetAtt DispatchFunction.Arn
          Input: '{"body":"{\"action\":\"cleanup\"}","headers":{}}'

  CleanupPermission:
    Type: AWS::Lambda::Permission
    Properties:
      FunctionName: !Ref DispatchFunction
      Action: lambda:InvokeFunction
      Principal: events.amazonaws.com
      SourceArn: !GetAtt CleanupRule.Arn

  # --- Log Group ---
  CILogGroup:
    Type: AWS::Logs::LogGroup
    Properties:
      LogGroupName: /tinqs/ci
      RetentionInDays: 14

Outputs:
  WebhookURL:
    Description: Configure as Gitea system webhook
    Value: !Sub 'https://${WebhookApi}.execute-api.${AWS::Region}.amazonaws.com/prod/webhook'
  DispatchArn:
    Value: !GetAtt DispatchFunction.Arn
  ExecArn:
    Value: !GetAtt ExecFunction.Arn
  RunsTable:
    Value: !Ref RunsTable
