openapi: 3.0.3
info:
  title: Domain Settings API
  description: >
    API used to manage domain settings such as public encryption keys
  license:
    name: Telenor Connexion Public License - v 1.0
    url: https://www.telenorconnexion.com
  termsOfService: https://www.telenorconnexion.com/terms-of-service
  contact:
    name: Telenor Connexion Support
    email: cno@telenorconnexion.com
  version: 1.0.0
servers:
  - url: https://api.iot.telenor.com

x-amazon-apigateway-request-validators:
  none:
    validateRequestBody: false
    validateRequestParameters: false
x-amazon-apigateway-request-validator: none
x-amazon-apigateway-gateway-responses:
  DEFAULT_4XX:
    responseParameters: &base-gateway-response
      gatewayresponse.header.Access-Control-Allow-Origin: "'*'"
      gatewayresponse.header.Access-Control-Allow-Headers: "'Authorization,Content-Type,Content-Language,Accept,Accept-Language,Origin,X-Requested-With,X-Amz-Date,X-Api-Key,X-Amz-Security-Token,Cache-Control'"
      gatewayresponse.header.Access-Control-Allow-Methods: "'GET,HEAD,POST,PUT,DELETE,CONNECT,OPTIONS,TRACE,PATCH'"
  DEFAULT_5XX:
    responseParameters: *base-gateway-response
  # 401 Error returned from the authorizer when the token is not valid
  UNAUTHORIZED:
    responseParameters: *base-gateway-response
    responseTemplates:
      'application/json': |
        {
          "message": "Unauthorized. The Authorization token in the header is not valid. Please renew the token and try again."
        }
  # 403 The policy generated by the authorizer doesn't permit access to the resource requested.
  ACCESS_DENIED:
    responseParameters: *base-gateway-response
    responseTemplates:
      'application/json': |
        {
          "message": "Access denied. You are not permitted to access the requested resource."
        }

paths:
  /iot-connect/domain-settings/v1/encryption-keys/upload:
    post:
      x-amazon-apigateway-integration: &aws-gateway
        uri:
          Fn::Sub: arn:aws:apigateway:${AWS::Region}:lambda:path/2015-03-31/functions/${DomainSettingsApiLambda.Arn}/invocations
        passthroughBehavior: when_no_match
        httpMethod: POST
        type: aws_proxy
      tags:
        - Public Encryption Keys
      summary: Add public encryption key via file upload.
      description: Adds a public PGP encryption keys associated with supplied domainId and name. A maximum of 10 keys per domain is allowed. Key size must be > 2047 bits.
      requestBody:
        description: Payload for adding a public encryption key.
        required: true
        content:
          multipart/form-data:
            schema:
              $ref: '#/components/schemas/uploadEncryptionKey'
      responses:
        201:
          description: Public encryption key added successfully.
          headers:
            Content-Location:
              $ref: '#/components/headers/content-Location'
        400: &error
          $ref: '#/components/responses/problemResponse'
        429: *error
        500: *error
  /iot-connect/domain-settings/v1/encryption-keys:
    post:
      x-amazon-apigateway-integration: &aws-gateway
        uri:
          Fn::Sub: arn:aws:apigateway:${AWS::Region}:lambda:path/2015-03-31/functions/${DomainSettingsApiLambda.Arn}/invocations
        passthroughBehavior: when_no_match
        httpMethod: POST
        type: aws_proxy
      tags:
        - Public Encryption Keys
      summary: Add public encryption key.
      description: Adds a public PGP encryption keys associated with supplied domainId and name. A maximum of 10 keys per domain is allowed. Key size must be > 2047 bits.
      requestBody:
        description: Payload for adding a public encryption key.
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/addEncryptionKey'
        required: true
      responses:
        201:
          description: Public encryption key added successfully.
          headers:
            Content-Location:
              $ref: '#/components/headers/content-Location'
        400: *error
        429: *error
        500: *error
    get:
      x-amazon-apigateway-integration: *aws-gateway
      tags:
        - Public Encryption Keys
      summary: Get public encryption keys.
      description: Fetches all public encryption keys associated with the client's managed domains. If the domainId query parameter is omitted, all keys for the domain and all subdomains managed by the user will be included.
      parameters:
        - name: domainId
          in: query
          required: false
          schema:
            type: string
          description: Filter public encryption keys by a specific domainId.
          example: 1bu9s9t4-aowyi08t
      responses:
        200:
          description: A list of public encryption keys.
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/encryptionKey'
        429: *error
        500: *error
  /iot-connect/domain-settings/v1/encryption-keys/{id}:
    get:
      x-amazon-apigateway-integration: *aws-gateway
      tags:
        - Public Encryption Keys
      summary: Get public encryption key by ID.
      description: Fetches a public encryption key for the specified ID.
      parameters:
        - name: id
          in: path
          description: The encryption key ID.
          required: true
          schema:
            type: string
      responses:
        200:
          description: A single encryption key.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/encryptionKey'
        404: *error
        429: *error
        500: *error
    delete:
      x-amazon-apigateway-integration: *aws-gateway
      tags:
        - Public Encryption Keys
      summary: Delete a public encryption key by ID.
      description: Removes a public encryption key for the specified ID.
      parameters:
        - name: id
          in: path
          description: The encryption key ID.
          required: true
          schema:
            type: string
      responses:
        204:
          description: Public encryption key deleted successfully.
        404: *error
        429: *error
        500: *error

components:
  schemas:
    encryptionKey:
      type: object
      required:
        - id
        - name
        - key
        - domainId
        - createdAt
      properties:
        id:
          type: string
        name:
          $ref: '#/components/schemas/keyName'
        key:
          $ref: '#/components/schemas/publicPGPKey'
        domainId:
          $ref: '#/components/schemas/domainId'
        createdAt:
          type: string
          format: date-time

    publicPGPKey:
      type: string
      description: |
        The PGP public key file with at least a key size > 2047 bits.
        Must start with '-----BEGIN PGP PUBLIC KEY BLOCK-----' and end with '-----END PGP PUBLIC KEY BLOCK-----'.
      example: |
        -----BEGIN PGP PUBLIC KEY BLOCK-----
        Comment: My OpenPGP certificate

        xsBNBFzF5PABCAC3Sge+FDs....
        -----END PGP PUBLIC KEY BLOCK-----

    publicPGPKeyFile:
      type: string
      format: binary
      description: |
        The PGP public key file with at least a key size > 2047 bits.
      example: public.key
    
    keyName:
      type: string
      description: The name of the public encryption key.
      example: My key
      minLength: 3
      maxLength: 50
    
    domainId:
      type: string
      description: Domain the resource belongs to. Used to determine which users have access to the resource.
      pattern: ^([A-Za-z0-9]{8}-){0,6}[A-Za-z0-9]{8}$
      example: a1ce25s2-c23edcs9

    addEncryptionKey:
      type: object
      required:
        - name
        - key
        - domainId
      properties:
        name:
          $ref: '#/components/schemas/keyName'
        key:
          $ref: '#/components/schemas/publicPGPKey'
        domainId:
          $ref: '#/components/schemas/domainId'
    
    uploadEncryptionKey:
      type: object
      required:
        - name
        - key
        - domainId
      properties:
        name:
          $ref: '#/components/schemas/keyName'
        key:
          $ref: '#/components/schemas/publicPGPKeyFile'
        domainId:
          $ref: '#/components/schemas/domainId'

    error:
      type: object
      properties:
        description:
          type: string
        errorCode:
          type: string
        timestamp:
          type: string
          format: date-time

    problemDetails:
      type: object
      description: RFC 9457 compliant problem details object for HTTP APIs.
      required:
        - type
        - title
        - status
        - detail
      properties:
        type:
          type: string
          format: uri
          description: A URI reference that identifies the problem type.
          enum:
            - urn:api.iot.telenor.com:problems:bad-gateway
            - urn:api.iot.telenor.com:problems:bad-request
            - urn:api.iot.telenor.com:problems:gateway-timeout
            - urn:api.iot.telenor.com:problems:internal-server-error
            - urn:api.iot.telenor.com:problems:not-found
            - urn:api.iot.telenor.com:problems:too-many-requests
            - urn:api.iot.telenor.com:problems:unsupported-media-type
            # Domain-specific problem types
            - urn:api.iot.telenor.com:problems:bad-request:settings:invalid-domain-id
            - urn:api.iot.telenor.com:problems:bad-request:settings:invalid-request-body
            - urn:api.iot.telenor.com:problems:bad-request:settings:invalid-path-parameters
            - urn:api.iot.telenor.com:problems:bad-request:settings:too-many-encryption-keys
        title:
          type: string
          description: A short, human-readable summary of the problem.
        status:
          type: integer
          description: The HTTP status code for this occurrence of the problem.
        detail:
          type: string
          description: A human-readable explanation specific to this occurrence of the problem.
          example: The specified domain ID is invalid.
        instance:
          type: string
          format: uri
          description: Optional URI reference that identifies the specific occurrence of the problem.
          example: /iot-connect/domain-settings/v1/encryption-keys
        errors:
          type: array
          description: Optional array of field-level errors.
          items:
            type: object
            properties:
              detail:
                type: string
                description: Description of the validation error.
                example: Field X must be a positive integer
              pointer:
                type: string
                description: JSON Pointer to the field that caused the error.
                example: '#/quantity'
      additionalProperties: true
      example:
        type: urn:api.iot.telenor.com:problems:bad-request
        title: Bad Request
        status: 400
        detail: Invalid request body
        errors:
          - detail: The specified domain ID is invalid, or you are not authorized to create an encryption key on that domain.
            pointer: '#/domainId'

  headers:
    content-Location:
      description: URL to the resource that got impacted by the status change.
      schema:
        type: string
        format: url

  responses:
    problemResponse:
      description: RFC 9457 compliant problem details response.
      headers:
        Access-Control-Allow-Origin:
          schema:
            type: string
        Access-Control-Allow-Methods:
          schema:
            type: string
        Access-Control-Allow-Headers:
          schema:
            type: string
      content:
        application/problem+json:
          schema:
            $ref: '#/components/schemas/problemDetails'