$schema: 'http://support.riverbed.com/apis/service_def/2.2'
id: 'http://support.riverbed.com/apis/cmc.topology/1.0'
provider: 'riverbed'
name: cmc.topology
version: "1.0"
title: REST  API  for  SCC Sites  and  Uplinks

types:
    identifier:
        description: Generic  numeric  identifier
        type: integer
        minimum: 1
        readOnly: true

    unrestricted_name:
        description: Case sensitive name. Only alphanumeric, '-' and '_' are permitted.
        type: string
        pattern: '^[a-zA-Z0-9-][a-zA-Z0-9_-]*$|^[a-zA-Z0-9_-][a-zA-Z0-9 _-]+[a-zA-Z0-9_-]$'
        minLength: 1
        maxLength: 30

    ipv4address:
        description: IPv4 address (x.y.z.k)
        type: string
        pattern: '^((?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?))?$'

    ipv4prefix:
        description: IPv4 prefix (x.y.z.k/mask)
        type: string
        pattern: '^(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(/(3[012]|[12]?[0-9]))$'
        minLength: 9
        maxLength: 18

    hostname:
        description: Hostname
        type: string
        pattern: '^((([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9\-]*[a-zA-Z0-9])\.)*([A-Za-z0-9]|[A-Za-z0-9][A-Za-z0-9\-]*[A-Za-z0-9]))?$'
        maxLength: 255

    interface:
        description: In-path interface
        type: string
        pattern: '^inpath\d_\d|primary'

    bandwidth_down:
        description: "Download Bandwidth, in kbps"
        type: integer
        minimum: 1
        maximum: 10000000

    bandwidth_up:
        description: "Upload Bandwidth, in kbps"
        type: integer
        minimum: 1
        maximum: 10000000

    probe_dscp:
        description: "DSCP Marking for path probe packets"
        type: integer
        minimum: 0
        maximum: 63

    probe_timeout:
        description: "Timeout in seconds, for path probe packets"
        type: integer
        minimum: 1
        maximum: 10

    probe_threshold:
        description: "Number of probes to detect a path as UP/DOWN"
        type: integer
        minimum: 1
        maximum: 20

    positive_integer:
        type: integer
        minimum: 0

    appliance:
        description: Appliance Object
        type: object
        additionalProperties: false
        properties:
            id: { $ref: '#/types/identifier' }
            inventory_id:
                $merge:
                    source: { $ref: '#/types/identifier' }
                    with: { description: unique id of appliance inventory service }
            serial_number:
                type: string
                readOnly: true
            is_stc_member:
                description: True if this appliance is part of a secure transport
                    concentrator.
                type: boolean
                readOnly: true
        required: [inventory_id]

    site_uplink:
        description: Uplink object
        type: object
        additionalProperties: false
        properties:
            uplink_type_id: { $ref: '#/types/identifier' }
            uplink_type_name:
                $merge:
                    source: { $ref: '#/types/unrestricted_name' }
                    with: { readOnly: true }
            is_stc_uplink:
                description: "Is this uplink used by the Secure transport concentrator?"
                type: boolean
                readOnly: true
            bandwidth_down: { $ref: '#/types/bandwidth_down' }
            bandwidth_up: { $ref: '#/types/bandwidth_up' }
            gateway_ip: { $ref: '#/types/ipv4address' }
            interface: { $ref: '#/types/interface' }
            nat: { $ref: '#/types/ipv4address' }
            probe_dscp: {$ref: '#/types/probe_dscp' }
            probe_timeout: {$ref: '#/types/probe_timeout' }
            probe_threshold: {$ref: '#/types/probe_threshold' }
            is_firewalled:
                description: "Indicates whether the SteelHead accessing this Uplink is behind a firewall"
                type: boolean
            is_default:
                description: "Indicates whether it is used as the interface default uplink"
                type: boolean
        required: [uplink_type_id, bandwidth_down, bandwidth_up, interface, gateway_ip]

    stc_uplink:
        description: Uplink which belongs to the Secure Transport Concentrator
        type: object
        additionalProperties: false
        properties:
            uplink_type_id: { $ref: '#/types/identifier' }
            gateway_ip: { $ref: '#/types/ipv4address' }
        required: [uplink_type_id, gateway_ip]

    uplink:
        description: Uplink object
        type: object
        additionalProperties: false
        properties:
            uplink_type_id: { $ref: '#/types/identifier' }
            uplink_type_name:
                $merge:
                    source: { $ref: '#/types/unrestricted_name' }
                    with: { readOnly: true }
            bandwidth_down: { $ref: '#/types/bandwidth_down' }
            bandwidth_up: { $ref: '#/types/bandwidth_up' }
            gateway_ip: { $ref: '#/types/ipv4address' }
            interface: { $ref: '#/types/interface' }
            nat: { $ref: '#/types/ipv4address' }
            probe_dscp: {$ref: '#/types/probe_dscp' }
            probe_timeout: {$ref: '#/types/probe_timeout' }
            probe_threshold: {$ref: '#/types/probe_threshold' }
            is_firewalled:
                description: "Indicates whether the SteelHead accessing this Uplink is behind a firewall"
                type: boolean
            is_default:
                description: "Indicates whether it is used as the interface default uplink"
                type: boolean
        required: [uplink_type_id, bandwidth_down, bandwidth_up, interface]

    secure_transport_concentrator:
        description: A secure concentrator consists of a dedicated appliance with secure uplinks ..
        type: object
        properties:
            appliances:
                type: array
                items: {$ref: '#/types/appliance'}
            stc_uplinks:
                type: array
                items: {$ref: '#/types/stc_uplink'}
        required: [appliances, stc_uplinks]

    poller_response:
        type: object
        properties:
            poll_req_id:
                type: integer
                description: Request ID registered with poller
            serial:
                type: string
                description: Appliance from which response is received
            poll_time:
                type: timestamp
            resp_data:
                type: string
                description: Response from the polled request


resources:

############################################################
# /bandwidth_usage resources
############################################################

    bandwidth_usage:
        description: Gives the bandwidth usage for LAN in and WAN out for sites based on start and end time.
        type: object
        properties:
            start_time: {type: timestamp}
            end_time: {type: timestamp}
            total_lan:
                type: number
                readOnly: true
            total_wan:
                type: number
                readOnly: true
            data:
                type: array
                items:
                    type: object
                    additionalProperties: false
                    properties:
                        lan:
                            type: number
                            readOnly: true
                        wan:
                            type: number
                            readOnly: true
                        timestamp:
                            type: timestamp
                            readOnly: true
        additionalProperties: false

        links:
            self:
                description: Base URI for an instance of a site
                path: "$/bandwidth_usage"
                params:
                    site_id: {type: integer}
                    start_time: {type: timestamp}
                    end_time:  {type: timestamp}

            get:
                method: GET
                description: Get the bandwidth usage.
                response: { $ref: '#/resources/bandwidth_usage' }


############################################################
# /sites, /sites/{id} and /sites/appliances resources
############################################################

    site:
        description: Site object
        type: object
        additionalProperties: false
        required: [name, site_type_id, region_id, subnets]
        properties:
            id: {$ref: '#/types/identifier'}
            name: {$ref: '#/types/unrestricted_name'}
            site_type_id: { $ref: '#/types/identifier' }
            site_type_name:
                type: string
                readOnly: true
            region_id:
                $ref: '#/types/identifier'
            region_name:
                type: string
                readOnly: true
            description:
                type: string
                maxLength: 255
            address:
                type: object
                additionalProperties: false
                properties:
                    street:
                        type: string
                        maxLength: 127
                    city:
                        type: string
                        maxLength: 63
                    postal:
                        type: string
                        maxLength: 63
                    country:
                        type: string
                        maxLength: 63
            contact:
                type: object
                additionalProperties: false
                properties:
                    name:
                        type: string
                        maxLength: 127
                    title:
                        type: string
                        maxLength: 63
                    phone:
                        type: string
                        maxLength: 63
                    email:
                        type: string
                        maxLength: 255
            status:
                type: string
                readOnly: true
            mission_critical:
                type: boolean
            is_secure_capable:
                description: Indicates secure capability by site associated uplinks
                type: boolean
                readOnly: true
            subnets:
                type: array
                items: {$ref: '#/types/ipv4prefix'}

            appliances:
                description: All appliances in this site except those which are secure transport only appliances.
                type: array
                items:
                    $ref: '#/types/appliance'

            secure_transport_concentrators:
                description: An array of secure transport concentrator's
                type: array
                items:
                    $ref: '#/types/secure_transport_concentrator'

            uplinks:
                description: All uplinks at a site
                type: array
                items:
                    $ref: '#/types/site_uplink'
            is_backhaul_source:
                description: Indicates if site backhauls to another site.
                type: boolean
                readOnly: true
            is_backhaul_destination:
                description: Indicates if this site is backhauled to from another site.
                type: boolean
                readOnly: true
            backhaul_destination_site_id:
                $merge:
                    source: { $ref: '#/types/identifier' }
                    with: { description: "Id of the site to which we are backhauling to." }
            backhaul_source_site_ids:
                description: IDs of the site which backhauls to this site.
                type: array
                items: {$ref: '#/types/identifier'}
                readOnly: true

        relations:
            instances: {resource: '#/resources/sites'}

        links:
            self:
                description: Base URI for an instance of a site
                path: "$/sites/items/{id}"

            get:
                description: Retrieve the data representation of a site
                method: GET
                response: {$ref: '#/resources/site'}

            set:
                description: Replace the data representation for a site
                method: PUT
                request: {$ref: '#/resources/site'}
                response: {$ref: '#/resources/site'}

            delete:
                description: Delete a site instance
                method: DELETE

    brief_sites:
        description: List of Sites without the subnets
        type: array
        items:
            type: object
            properties:
                id: {$ref: '#/types/identifier'}
                name: {$ref: '#/types/unrestricted_name'}
                site_type_id: { $ref: '#/types/identifier' }
                site_type_name:
                    type: string
                    readOnly: true
                region_id:
                    $ref: '#/types/identifier'
                region_name:
                    type: string
                    readOnly: true
                description:
                    type: string
                    maxLength: 255
                address:
                    type: object
                    additionalProperties: false
                    properties:
                        street:
                            type: string
                            maxLength: 127
                        city:
                            type: string
                            maxLength: 63
                        postal:
                            type: string
                            maxLength: 63
                        country:
                            type: string
                            maxLength: 63
                contact:
                    type: object
                    additionalProperties: false
                    properties:
                        name:
                            type: string
                            maxLength: 127
                        title:
                            type: string
                            maxLength: 63
                        phone:
                            type: string
                            maxLength: 63
                        email:
                            type: string
                            maxLength: 255
                status:
                    type: string
                    readOnly: true
                mission_critical:
                    type: boolean
                is_secure_capable:
                    description: Indicates secure capability by site associated uplinks
                    type: boolean
                    readOnly: true

                appliances:
                    description: All appliances in this site, except those which are secure transport only appliances
                    type: array
                    items:
                        $ref: '#/types/appliance'

                secure_transport_concentrators:
                    description: An array of secure transport concentrators
                    type: array
                    items:
                        $ref: '#/types/secure_transport_concentrator'

                uplinks_count:
                    description: Count of uplinks at a site
                    type: number
                    readOnly: true
                stc_uplinks_count:
                    description: Count of stc uplinks at a site
                    type: number
                    readOnly: true
                is_backhaul_source:
                    description: Indicates if site backhauls to another site.
                    type: boolean
                    readOnly: true
                is_backhaul_destination:
                    description: Indicates if this site is backhauled to from another site.
                    type: boolean
                    readOnly: true
                backhaul_destination_site_id:
                    $merge:
                        source: { $ref: '#/types/identifier' }
                        with: { description: "Id of the site to which we are backhauling to." }
                backhaul_source_site_ids:
                    description: IDs of the site which backhauls to this site.
                    type: array
                    items: {$ref: '#/types/identifier'}
                    readOnly: true

        links:
            self:
                description: Base URI for list of brief sites
                path: "$/brief_sites"
                params:
                    name: {$ref: '#/types/unrestricted_name'}
                    serial_number:
                        type: string
                    site_type_id:
                        $ref: '#/types/identifier'
                    region_id:
                        $ref: '#/types/identifier'
                    is_backhaul_source:
                        type: boolean
                    is_backhaul_destination:
                        type: boolean
                    backhaul_destination_site_id:
                        $ref: '#/types/identifier'

            get:
                description: Get list of sites.
                method: GET
                response: {$ref: '#/resources/brief_sites'}

    sites:
        description: List of Sites
        type: array
        items:
            $merge:
                source: { $ref: '#/resources/site' }
                with:
                    relations:
                        full:
                            resource: '#/resources/site'
                            vars:
                                id: "0/id"

        links:
            self:
                description: Base URI for list of sites
                path: "$/sites"
                params:
                    name: {$ref: '#/types/unrestricted_name'}
                    serial_number:
                        type: string
                    site_type_id:
                        $ref: '#/types/identifier'
                    region_id:
                        $ref: '#/types/identifier'
                    is_backhaul_source:
                        type: boolean
                    is_backhaul_destination:
                        type: boolean
                    backhaul_destination_site_id:
                        $ref: '#/types/identifier'
                    has_stc:
                        type: boolean
                    status:
                        type: string

            get:
                description: Get list of sites.
                method: GET
                response: {$ref: '#/resources/sites'}

            create:
                description: Create a new site instance
                method: POST
                request: {$ref: '#/resources/site'}
                response: {$ref: '#/resources/site'}

            clear:
                description: Delete all site instances.
                method: POST
                path: "$/sites/clear"

    appliances:
        description: All appliances in sites
        type: array
        items:
            $ref: '#/types/appliance'

        links:
            self:
                description: Base URI for sites appliances resource
                path: "$/sites/appliances"
                params:
                    secure_capable:
                        description: filter sites by is_secure_capable
                        type: boolean

            get:
                description: Retrieve the data representation of appliances
                method: GET
                response: {$ref: '#/resources/appliances'}


############################################################
# /site_connectivity_templates and
# /site_connectivity_templates/{id} resources
############################################################
    site_connectivity_template:
        description: Template of site connectivity parameters
        type: object
        additionalProperties: false
        required: [name]
        properties:
            id: { $ref: '#/types/identifier' }
            name: { $ref: '#/types/unrestricted_name' }
            uplinks:
                description: Site uplinks template
                type: array
                items:
                    $ref: '#/types/uplink'

        relations:
            instances:
                resource: '#/resources/site_connectivity_templates'

        links:
            self:
                path: "$/site_connectivity_templates/items/{id}"
            get:
                method: GET
                response: { $ref: '#/resources/site_connectivity_template' }

            set:
                method: PUT
                request: { $ref: '#/resources/site_connectivity_template' }
                response: { $ref: '#/resources/site_connectivity_template' }

            delete:
                method: DELETE


    site_connectivity_templates:
        type: array
        items: { $ref: '#/resources/site_connectivity_template' }

        links:
            self:
                path: "$/site_connectivity_templates"
            create:
                method: POST
                request: { $ref: '#/resources/site_connectivity_template' }
                response: { $ref: '#/resources/site_connectivity_template' }
            get:
                method: GET
                response: { $ref: '#/resources/site_connectivity_templates' }

            clear:
                method: POST
                path: "$/site_connectivity_templates/clear"

############################################################
# /networks and /networks/{id} resources
############################################################

    network:
        description: Network object
        type: object
        additionalProperties: false
        properties:
            id:
                $merge:
                    source: { $ref: '#/types/identifier' }
                    with: { description: "Network ID" }
            name:
                $merge:
                    source: { $ref: '#/types/unrestricted_name' }
                    with: { description: "Network Name" }
            security_level:
                type: integer
                minimum: 0
                maximum: 1
            is_public:
                type: boolean
            is_built_in:
                type: boolean
                readOnly: true
        required: [name]
        relations:
            instances:
                resource: '#/resources/networks'

        links:
            self:
                description: Base URI for an instance of a Network
                path: "$/networks/items/{id}"

            get:
                description: Retrieve a data representation of a Network
                method: GET
                response:
                    $ref: '#/resources/network'

            set:
                description: Replace the data representation for a Network
                method: PUT
                request:
                    $ref: '#/resources/network'
                response:
                    $ref: '#/resources/network'

            delete:
                description: Delete a Network instance
                method: DELETE

    networks:
        description: List of Networks
        type: array
        items: { $ref: '#/resources/network' }

        links:
            self:
                description: Base URI for a list of Networks
                path: "$/networks"
                params:
                    name: {$ref: '#/types/unrestricted_name'}

            create:
                description: Create a new Network instance
                method: POST
                request:
                    $ref: '#/resources/network'
                response:
                    $ref: '#/resources/network'

            get:
                description: Get a list of Network instances.
                method: GET
                response:
                    $ref: '#/resources/networks'

            clear:
                description: Delete all the Network instances.
                method: POST
                path: "$/networks/clear"

############################################################
# /uplink_types and uplink_types/{id} resources
############################################################

    uplink_type:
        description: Type of uplinks for path selection
        type: object
        additionalProperties: false
        properties:
            id: { $ref: '#/types/identifier' }
            name: { $ref: '#/types/unrestricted_name' }
            network_id: { $ref: '#/types/identifier' }
            network_name:
                $merge:
                    source: { $ref: '#/types/unrestricted_name' }
                    with: { readOnly: true }
        required: [name, network_id]

        relations:
            instances:
                resource: '#/resources/uplink_types'
            network:
                resource: '#/resources/network'
                vars: { id: "0/network_id" }

        links:
            self:
                path: "$/uplink_types/items/{id}"

            get:
                method: GET
                response: { $ref: '#/resources/uplink_type' }

            set:
                method: PUT
                request: { $ref: '#/resources/uplink_type' }
                response: { $ref: '#/resources/uplink_type' }

            delete:
                method: DELETE

    uplink_types:
        description: List of uplink types
        type: array
        items: { $ref: '#/resources/uplink_type' }

        links:
            self:
                path: "$/uplink_types"
                params:
                    name: {$ref: '#/types/unrestricted_name'}
                    network_id:
                        $ref: '#/types/identifier'

            create:
                method: POST
                request: { $ref: '#/resources/uplink_type' }
                response: { $ref: '#/resources/uplink_type' }

            get:
                method: GET
                response: { $ref: '#/resources/uplink_types' }

            clear:
                method: POST
                path: "$/uplink_types/clear"


############################################################
# /site_types and site_types/{id} resources
############################################################

    site_type:
        description: Type of category and function of the site
        type: object
        additionalProperties: false
        properties:
            id: { $ref: '#/types/identifier' }
            name: {$ref: '#/types/unrestricted_name'}
            description:
                type: string
                maxLength: 120
            is_built_in:
                type: boolean
                readOnly: True
        required: [name]

        relations:
            instances:
                resource: '#/resources/site_types'

        links:
            self:
                path: "$/site_types/items/{id}"

            get:
                method: GET
                response: { $ref: '#/resources/site_type' }

            set:
                method: PUT
                request: { $ref: '#/resources/site_type' }
                response: { $ref: '#/resources/site_type' }

            delete:
                method: DELETE

    site_types:
        description: List of site types
        type: array
        items:
            type: object
            properties:
                id: { $ref: '#/types/identifier' }
                name: {$ref: '#/types/unrestricted_name'}
                description:
                    type: string
                    maxLength: 120
                is_built_in:
                    type: boolean
                    readOnly: True

            relations:
                full:
                    resource: '#/resources/site_type'
                    vars:
                        id: "0/id"

        links:
            self:
                path: "$/site_types"
                params:
                    name:
                        type: string

            create:
                method: POST
                request: { $ref: '#/resources/site_type' }
                response: { $ref: '#/resources/site_type' }

            get:
                method: GET
                response: { $ref: '#/resources/site_types' }

            clear:
                method: POST
                path: "$/site_types/clear"


    site_type_stats:
        description: "Get the status for a site."
        type: object
        properties:
            site_type_id: {type: integer}
            start_time: {type: timestamp}
            end_time: {type: timestamp}
            status:
                type: string
                readOnly: true
            normal_status_count:
                type: integer
                readOnly: true
            critical_status_count:
                type: integer
                readOnly: true
            warning_status_count:
                type: integer
                readOnly: true
        additionalProperties: false

        links:
            self:
                path: "$/site_types/items/{site_type_id}/stats"
                params:
                    start_time: {type: timestamp}
                    end_time: {type: timestamp}

            get:
                method: GET
                response: { $ref: '#/resources/site_type_stats' }


############################################################
# /regions and regions/{id} resources
############################################################

    region:
        description: Physical region of the property
        type: object
        additionalProperties: false
        properties:
            id: { $ref: '#/types/identifier' }
            name: {$ref: '#/types/unrestricted_name'}
        required: [name]

        relations:
            instances:
                resource: '#/resources/regions'

        links:
            self:
                path: "$/regions/items/{id}"

            get:
                method: GET
                response: { $ref: '#/resources/region' }

            set:
                method: PUT
                request: { $ref: '#/resources/region' }
                response: { $ref: '#/resources/region' }

            delete:
                method: DELETE

    regions:
        description: List of regions
        type: array
        items: { $ref: '#/resources/region' }

        links:
            self:
                path: "$/regions"
                params:
                    # Allow filtering
                    name: {$ref: '#/types/unrestricted_name'}

            create:
                method: POST
                request: { $ref: '#/resources/region' }
                response: { $ref: '#/resources/region' }

            get:
                method: GET
                response: { $ref: '#/resources/regions' }

            clear:
                method: POST
                path: "$/regions/clear"


############################################################
## /uplink_status resources
#############################################################
    uplink_status:
        description: Read only detailed description of the status of uplink.
        type: array
        items:
            type: object
            additionalProperties: false
            properties:
                site_type_id: {$ref: '#/types/identifier'}
                site_type_path_status:
                    type: array
                    items:
                        type: object
                        additionalProperties: false
                        properties:
                            path_status:
                                type: string
                            path_count:
                                description: The number of paths that have this path_status from the current site_type.
                                type: number
                            site_count:
                                description: The number of sites that have this path_status from the current site_type.
                                type: number
                # XXX: this should be called site_details instead?
                site_type_details:
                    type: array
                    items:
                        type: object
                        additionalProperties: false
                        properties:
                            site_id: { $ref: '#/types/identifier'}
                            uplink_status:
                                type: array
                                items:
                                    type: object
                                    additionalProperties: false
                                    properties:
                                        id: {$ref: '#/types/identifier'}
                                        status:
                                            type: string
                            site_reachability_status:
                                type: array
                                items:
                                    type: object
                                    additionalProperties: false
                                    properties:
                                        site_name:
                                            type: string
                                        reachability_status:
                                            type: string
                            path_status:
                                type: array
                                items:
                                    type: object
                                    additionalProperties: false
                                    properties:
                                        path_status:
                                            type: string
                                        path_count:
                                            type: number
                            appliances:
                                type: array
                                items:
                                    type: object
                                    additionalProperties: false
                                    properties:
                                        serialnum: {$ref: '#/types/identifier'}
                                        uplinks:
                                            type: array
                                            items:
                                                type: object
                                                additionalProperties: false
                                                properties:
                                                    uplink_name:
                                                        type: string
                                                    remote_sites:
                                                        type: array
                                                        items:
                                                            type: object
                                                            additionalProperties: false
                                                            properties:
                                                                remote_site_name:
                                                                    type: string
                                                                peers:
                                                                    type: array
                                                                    items:
                                                                        type: object
                                                                        additionalProperties: false
                                                                        properties:
                                                                                peer_ip:
                                                                                    type: string
                                                                                peer_status: { $ref: '#/types/ipv4address' }

        links:
            self:
                description: Base URI for getting uplink status
                path: "$/uplink_status"
                # Allow filtering by site id.
                params:
                    site_id:
                        $ref: '#/types/identifier'
                    site_type_id:
                        $ref: '#/types/identifier'

            get:
                description: Get the uplink_status.
                method: GET
                response:
                    $ref: '#/resources/uplink_status'

    poller:
        type: object
        description: Callback for polled requests to the appliance

        links:
            self:
                path: "$/poller_callback"

            callback:
                method: POST
                description: Callback to get polled response
                request:
                    $ref: '#/types/poller_response'
