openapi: "3.0.3"
info:
  description: Service that allows the consumers to be notified when something has changed in their e-Box enterprise ecosystem.
  version: "1.0"
  title: e-Box Enterprise Event Notification REST API
  contact:
    name: eBoxIntegration
    email: eBoxIntegration@smals.be
  license:
    name: e-Box
    url: http://www.digitalbelgium.be
security:
  - Oauth:
      [ 'scope:document:management:notification:events','scope:document:management:notification:monitoring','scope:document:management:consult:ws-eboxrestentreprise:documentprovider']
tags:
  - name: EventNotifications
  - name: Monitoring
servers:
  - url: "/REST/ebox/enterprise/eventNotification/v1"
paths:
  /health:
    get:
      tags:
        - Monitoring
      summary: Check health of the service
      description: This resource is only available to supervision users
      operationId: checkHealth
      externalDocs:
        url: "https://www.belgif.be/specification/rest/api-guide/#health"
      responses:
        "200":
          description: The service is UP, DEGRADED, DOWN
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/HealthStatus"
              examples:
                responseUp:
                  value:
                    {
                      "status": "UP"
                    }
                responseDegraded:
                  value:
                    {
                      "status": "DEGRADED"
                    }
        "503":
          description: The Service is unavailable
        default:
          description: "error payload"
          content:
            application/problem+json:
              schema:
                $ref: "#/components/schemas/Problem"
      security:
        - Oauth:
            [ 'scope:document:management:notification:monitoring' ]

  /eventNotifications:
    post:
      tags:
        - EventNotifications
      description: creates a new Event notification and propagates it to all subscribed document providers through the webhook endpoint of the common Message Registry API
      operationId: createEventNotification
      requestBody:
        required: true
        content:
          application/cloudevents+json:
            schema:
              $ref: '#/components/schemas/DocumentProviderNotificationEvent'
            examples:
              routingRuleDeleted:
                $ref: '#/components/examples/RoutingRuleDeleted'
              routingRuleCreated:
                $ref: '#/components/examples/RoutingRuleCreated'
              routingRuleUpdated:
                $ref: '#/components/examples/RoutingRuleUpdated'
              partitionCreated:
                $ref: '#/components/examples/PartitionCreated'
              partitionDeleted:
                $ref: '#/components/examples/PartitionDeleted'
              userPartitionRightsAdded:
                $ref: '#/components/examples/UserPartitionRightsAdded'
              userPartitionRightsRemoved:
                $ref: '#/components/examples/UserPartitionRightsRemoved'
      responses:
        201:
          description: created
        default:
          description: "error payload"
          content:
            application/problem+json:
              schema:
                $ref: "#/components/schemas/Problem"
      security:
        - Oauth:
            [ 'scope:document:management:notification:events' ]

components:
  examples:
    UserPartitionRightsAdded:
      value:
        specversion: "1.0"
        id: "550e8400-e29b-41d4-a716-446655440003"
        subject: "0677932208"
        time: "2025-03-25T14:00:00Z"
        dataschema: "https://dev.eboxenterprise.be/docs/spec/specifications#event-notification"
        source: "documentmanagement:publication:eboxenterprise:client:public"
        type: "be.eboxenterprise.userPartitionRights.rightAdded.v1"
        datacontenttype: "application/json"
        data:
          enterpriseNumber: "0406798006"
          partitionId: "HRdepartment"
          userSsin: "44022722580"
    UserPartitionRightsRemoved:
      value:
        specversion: "1.0"
        id: "550e8400-e29b-41d4-a716-446655440003"
        subject: "0677932208"
        time: "2025-03-25T14:00:00Z"
        dataschema: "https://dev.eboxenterprise.be/docs/spec/specifications#event-notification"
        source: "documentmanagement:publication:eboxenterprise:client:public"
        type: "be.eboxenterprise.userPartitionRights.rightRemoved.v1"
        datacontenttype: "application/json"
        data:
          enterpriseNumber: "0406798006"
          partitionId: "HRdepartment"
          userSsin: "44022722580"
    UserPartitionRightsCreated:
      value:
        specversion: "1.0"
        id: "550e8400-e29b-41d4-a716-446655440003"
        subject: "0677932208"
        time: "2025-03-25T14:00:00Z"
        dataschema: "https://dev.eboxenterprise.be/docs/spec/specifications#event-notification"
        source: "documentmanagement:publication:eboxenterprise:client:public"
        type: "be.eboxenterprise.userPartitionRights.rightAdded.v1"
        datacontenttype: "application/json"
        data:
          enterpriseNumber: "0406798006"
          partitionId: "HRdepartment"
          userSsin: "44022722580"

    PartitionCreated:
      value:
        specversion: "1.0"
        id: "550e8400-e29b-41d4-a716-446655440002"
        subject: "0677932208"
        time: "2025-03-25T14:00:00Z"
        dataschema: "https://dev.eboxenterprise.be/docs/spec/specifications#event-notification"
        source: "documentmanagement:publication:eboxenterprise:client:public"
        type: "be.eboxenterprise.partition.created.v1"
        datacontenttype: "application/json"
        data:
          enterpriseNumber: "0406798006"
          partitionId: "HRdepartment"
    PartitionDeleted:
      value:
        specversion: "1.0"
        id: "550e8400-e29b-41d4-a716-446655440002"
        subject: "0677932208"
        time: "2025-03-25T14:00:00Z"
        dataschema: "https://dev.eboxenterprise.be/docs/spec/specifications#event-notification"
        source: "documentmanagement:publication:eboxenterprise:client:public"
        type: "be.eboxenterprise.partition.deleted.v1"
        datacontenttype: "application/json"
        data:
          enterpriseNumber: "0406798006"
          partitionId: "HRdepartment"
    RoutingRuleCreated:
      value:
        specversion: "1.0"
        id: "550e8400-e29b-41d4-a716-446655440001"
        subject: "0677932208"
        time: "2025-03-25T14:00:00Z"
        dataschema: "https://dev.eboxenterprise.be/docs/spec/specifications#event-notification"
        source: "documentmanagement:publication:eboxenterprise:client:public"
        type: "be.eboxenterprise.routingRule.created.v1"
        datacontenttype: "application/json"
        data:
          enterpriseNumber: "0406798006"
          routingRuleId: 123
          orderedRoutingRules:
            items:
              - routingRuleId: 123
                priority: 1
                conditions:
                  - messageTypeId: "MT123"
                    senderApplicationId: "APP001"
                    senderOrganizationId: "0123456789"
                targetPartitionId: "finance"
                creationDate: "2025-07-18T10:00:00Z"
    RoutingRuleDeleted:
      value:
        specversion: "1.0"
        id: "550e8400-e29b-41d4-a716-446655440001"
        subject: "0677932208"
        time: "2025-03-25T14:00:00Z"
        dataschema: "https://dev.eboxenterprise.be/docs/spec/specifications#event-notification"
        source: "documentmanagement:publication:eboxenterprise:client:public"
        type: "be.eboxenterprise.routingRule.deleted.v1"
        datacontenttype: "application/json"
        data:
          enterpriseNumber: "0406798006"
          routingRuleId: 123
          orderedRoutingRules:
            items:
              - routingRuleId: 123
                priority: 1
                conditions:
                  - messageTypeId: "MT123"
                    senderApplicationId: "APP001"
                    senderOrganizationId: "0123456789"
                targetPartitionId: "finance"
                creationDate: "2025-07-18T10:00:00Z"
    RoutingRuleUpdated:
      value:
        specversion: "1.0"
        id: "550e8400-e29b-41d4-a716-446655440001"
        subject: "0677932208"
        time: "2025-03-25T14:00:00Z"
        dataschema: "https://dev.eboxenterprise.be/docs/spec/specifications#event-notification"
        source: "documentmanagement:publication:eboxenterprise:client:public"
        type: "be.eboxenterprise.routingRule.updated.v1"
        datacontenttype: "application/json"
        data:
          enterpriseNumber: "0406798006"
          routingRuleId: 123
          orderedRoutingRules:
            items:
              - routingRuleId: 123
                priority: 1
                conditions:
                  - messageTypeId: "MT123"
                    senderApplicationId: "APP001"
                    senderOrganizationId: "0123456789"
                targetPartitionId: "finance"
                creationDate: "2025-07-18T10:00:00Z"

  parameters:
    EventTypeId:
      name: eventTypeId
      in: path
      required: true
      schema:
        type: string
        description: "The identifier of the event type"
        example: RoutingRuleNotification

  schemas:
    HealthStatus:
      description: Response message for the API health
      type: object
      properties:
        status:
          description: "Level indicating the health status of the service: UP (functioning as expected), DOWN (suffering unexpected failures), DEGRADED (partly unavailable but service can be continued with reduced functionality), or a custom status value"
          type: string
          enum:
            - 'UP'
            - 'DOWN'
            - 'DEGRADED'
          x-ignore-rules:
            "cod-design": "Must be uppercase to be aligned with standard frameworks like springboot"
      required:
        - status
    CloudEventBase: # extend this schema with allOf to define schemas for specific events, with constraints on data/data_base64 and type
      type: object
      properties:
        specversion:
          type: string
          minLength: 1
          description: The version of the CloudEvents specification which the event uses.
          example: "1.0"
        id:
          type: string
          minLength: 1
          description: Identifies the event. Producers MUST ensure that source + id is unique for each distinct event. If a duplicate event is re-sent (e.g. due to a network error) it MAY have the same id. Consumers MAY assume that Events with identical source and id are duplicates.
          example: "550e8400-e29b-41d4-a716-446655440000"
        source:
          type: string
          format: uri-reference
          minLength: 1
          description: >
            Identifies the context in which an event happened.<br>
            Often this will include information such as the type of the event source, the organization publishing the event or the process that produced the event. The exact syntax and semantics behind the data encoded in the URI is defined by the event producer.<br>
            
            Producers MUST ensure that source + id is unique for each distinct event.<br>
            
            An application MAY assign a unique source to each distinct producer, which makes it
            easy to produce unique IDs since no other producer will have the same source.
            The application MAY use UUIDs, URNs, DNS authorities or an application-specific
            scheme to create unique source identifiers.<br>
            
            An absolute URI is RECOMMENDED
          example: "urn:event-source:nsso:employer-register"
        datacontenttype:
          type: string
          minLength: 1
          description: Media type of the payload (values of data or data_base64).
            MUST adhere to the format specified in RFC 2046.
          default: "application/json"
          nullable: true
          x-ignore-rules:
            jsn-null: allow null to comply with CloudEvents 1.0 spec
        subject:
          type: string
          minLength: 1
          description: Subject of the event (optional, may also be only present in payload)
          example: "employer:123456"
          nullable: true
          x-ignore-rules:
            jsn-null: allow null to comply with CloudEvents 1.0 spec
        time:
          type: string
          format: date-time
          description: Timestamp of when the occurrence happened. If the time of the occurrence cannot be determined then this attribute MAY be set to some other time (such as the current time) by the CloudEvents producer, however all producers for the same source MUST be consistent in this respect. In other words, either they all use the actual time of the occurrence or they all use the same algorithm to determine the value used.
          nullable: true
          x-ignore-rules:
            jsn-null: allow null to comply with CloudEvents 1.0 spec
        dataschema:
          description: Identifies the schema that data adheres to. Incompatible changes to the schema SHOULD be reflected by a different URI.
          type: string
          minLength: 1
          nullable: true
          format: uri
          x-ignore-rules:
            jsn-null: allow null to comply with CloudEvents 1.0 spec
      required: [id, specversion, source]
    Problem:
      description: A Problem Details object (RFC 7807)
      type: object
      properties:
        type:
          type: string
          format: uri
          description: An absolute URI that identifies the problem type
        href:
          type: string
          format: uri
          description: An absolute URI that, when dereferenced, provides human-readable documentation for the problem type (e.g. using HTML).
        title:
          type: string
          description: A short summary of the problem type. Written in English and readable for engineers (usually not suited for non technical stakeholders and not localized).
          example: Service Unavailable
        status:
          type: integer
          format: int32
          description: The HTTP status code generated by the origin server for this occurrence of the problem.
          minimum: 400
          maximum: 600
          exclusiveMaximum: true # "If you have an error here, you are probably using the wrong JSON Schema specification or the unstable version editor-next.swagger.io . See https://github.com/belgif/openapi-problem/issues/11"
          example: 503
        detail:
          type: string
          description: A human-readable explanation specific to this occurrence of the problem
        instance:
          type: string
          format: uri
          description: An absolute URI reference that identifies the specific occurrence of the problem. It may or may not yield further information if dereferenced.
    DocumentProviderNotificationEvent:
      type: object
      allOf:
        - $ref: "#/components/schemas/CloudEventBase"
      properties:
        type:
          type: string
          minLength: 1
          enum:
            - "be.eboxenterprise.v1.routingRule.created"
            - "be.eboxenterprise.v1.routingRule.updated"
            - "be.eboxenterprise.v1.routingRule.deleted"
            - "be.eboxenterprise.v1.partition.created"
            - "be.eboxenterprise.v1.partition.deleted"
            - "be.eboxenterprise.v1.userPartitionRights.rightAdded"
            - "be.eboxenterprise.v1.userPartitionRights.rightRemoved"
          x-ignore-rules:
            "cod-design": "event types use reverse DNS dot-notation"
      required: [type]
      discriminator:
        propertyName: type
        mapping:
          "be.eboxenterprise.v1.routingRule.created": RoutingRuleEvent
          "be.eboxenterprise.v1.routingRule.updated": RoutingRuleEvent
          "be.eboxenterprise.v1.routingRule.deleted": RoutingRuleEvent
          "be.eboxenterprise.v1.partition.created": PartitionEvent
          "be.eboxenterprise.v1.partition.deleted": PartitionEvent
          "be.eboxenterprise.v1.userPartitionRights.rightAdded": UserPartitionRightsEvent
          "be.eboxenterprise.v1.userPartitionRights.rightRemoved": UserPartitionRightsEvent
    EnterpriseNumber:
      description: Identifier issued by CBE for a registered organization
      type: string
      pattern: '^[0-1]?\d{9}$'
      example: "0406798006"

    RoutingRule:
      description: Partition rule to ease the receipt of this kind of messages
      type: object
      required:
        - routingRuleId
        - priority
        - conditions
        - targetPartitionId
      properties:
        routingRuleId:
          type: integer
          description: Routing rule technical identifier
        priority:
          type: integer
          minimum: 0
          description: "The position in the list of routing rules if the list is ordered by priority. The higher is this number, the less priority has the routing rule. For example, if the priority number is 5, this rule must be applied to messages matching the condition instead of the rules that have a higher priority number and with matching condition. There should not be routing rules with the same priority number. If a routing rule is created, the routing rule having the same priority number and all other routing rules having a higher priority number should have their priority number incremented by 1."
        conditions:
          type: array
          items:
            type: object
            description: "Criteria to follow to map a message to a partition. If a property is not given or has a null value, it means that the property can have any value like a wildcard. For example, if condition:{senderApplicationId:myApplication, senderOrganizationId:0123456789} then it means that every new messages from the organization 0123456789 and the sender application myApplication should be moved to the target partition."
            properties:
              messageTypeId:
                type: string
                description: identification of the message type
              senderApplicationId:
                type: string
                description: identification of the sender application
              senderOrganizationId:
                $ref: "#/components/schemas/EnterpriseNumber"
        targetPartitionId:
          type: string
          description: the partition where the new messages matching the condition must be moved to.
        creationDate:
          type: string
          description: Date when the user created the routing rule
          format: date-time

    OrderedRoutingRules:
      description: "Partition routing rules on an ebox already ordered from the highest priority to the lowest priority."
      type: "array"
      items:
        $ref: "#/components/schemas/RoutingRule"

    Ssin:
      description: Social Security Identification Number issued by the National Register or CBSS
      type: string
      pattern: '^\d{11}$'
      example: "44022722580"

    # NOTIFICATION SCHEMA
    # The objects below are marked as never used by swagger editor but are used and inherit from DocumentProviderNotificationEvent
    RoutingRuleEvent:
      description: "This object inherit from DocumentProviderNotificationEvent and define the data object with the notification schema for a notification about a newly created routing rule."
      type: object
      allOf:
        - $ref: "#/components/schemas/DocumentProviderNotificationEvent"
      required:
        - data
      properties:
        data:
          $ref: "#/components/schemas/RoutingRuleEventData"
    RoutingRuleEventData:
      description: Data specific to the routing rule event
      type: object
      properties:
        enterpriseNumber:
          $ref: "#/components/schemas/EnterpriseNumber"
        routingRuleId:
          type: integer
          description: The technical identifier of the added, modified or deleted routing rule. If this is an added or modified routing rule, it can be found in the list of routing rules in the property orderedRoutingRules.
        orderedRoutingRules:
          $ref: "#/components/schemas/OrderedRoutingRules"
      required: [ routingRuleId, orderedRoutingRules ]

    PartitionEvent:
      description: "This object inherit from DocumentProviderNotificationEvent and define the data object with the notification schema for a notification about a newly created partition."
      type: object
      allOf:
        - $ref: "#/components/schemas/DocumentProviderNotificationEvent"
      required:
        - data
      properties:
        data:
          $ref: "#/components/schemas/PartitionEventData"

    PartitionEventData:
      description: "data specific to the Partition event"
      type: object
      properties:
        enterpriseNumber:
          $ref: "#/components/schemas/EnterpriseNumber"
        partitionId:
          description: "The partition business identifier"
          type: "string"
          example: "HRdepartment"
      required: [ enterpriseNumber, partitionId ]
    UserPartitionRightsEvent:
      description: "This object inherit from DocumentProviderNotificationEvent and define the data object with the notification schema for a notification about a new access given to a human user to consult a partition"
      type: object
      allOf:
        - $ref: "#/components/schemas/DocumentProviderNotificationEvent"
      required:
        - data
      properties:
        data:
          $ref: "#/components/schemas/UserPartitionRightsEventData"

    UserPartitionRightsEventData:
      description: data specific to the userPartitionRights event
      type: object
      properties:
        enterpriseNumber:
          $ref: "#/components/schemas/EnterpriseNumber"
        partitionId:
          description: "The partition business identifier"
          type: "string"
          example: "HRdepartment"
        userSsin:
          $ref: "#/components/schemas/Ssin"
      required: [ enterpriseNumber, partitionId, userSsin ]


  securitySchemes:
    Oauth:
      type: oauth2
      flows:
        clientCredentials:
          tokenUrl: 'https://privateservices-int.socialsecurity.be/REST/oauth/v5/token'
          scopes:
            'scope:document:management:notification:events': "This scope allows a notification producer to push a notification."
            'scope:document:management:consult:ws-eboxrestentreprise:documentprovider': "This scope is given to ebox Document Providers and allows to consult event types."
            'scope:document:management:notification:monitoring': "This scope is given to monitoring applications to perform health checks."


