ApiRoute

The node is used for the specific endpoint description. Its interface is smilar to the one of a RequestStep node. No surprises, in both cases we deal with HTTP requests.

The main features of an ApiRoute node are:

  • Describing request HTTP headers, query parameters, body parameters and response HTTP codes, HTTP headers and body parameters;

  • Using types for describing every header, query parameter, and body parameter. Supported types: string, number, integer, boolean, array, and object;

  • Describing every entity;

  • Describing a number of request body parameters (based on content-type);

  • Describing a number of possible responses;

  • Creating a request out of the description;

  • Autocompletion of URLs, HTTP headers, query and body parameters in RequestStep nodes.

Interface Overview

To create an ApiRoute node right-click in the ApiFolder node and choose Add node -> ApiRoute.

An ApiRoute node in the project tree

This is how it looks like in the project tree:

The icon of these nodes is the HTTP method name. An ApiRoute node has the following context menu:

  • Rename. Change the node name.

  • Duplicate. Make a copy of the node. The new node will be named NodeName [Copy [number]].

  • Remove node. Use it to delete the node.

  • Show in explorer. Open the folder with the node in the file manager.

The ApiRoute Tab Interface

The ApiRoute node tab looks like this:

General Request Parameters

Look a little closer at the top part of the tab:

In the screenshot you can see the following parts of the interface.

  1. HTTP method. The list of available methods is identical to the one of RequestStep nodes.

  2. The Variables dialog button.

  3. The button to create a request out of the current API description.

  4. The request description (text).

Request parameters description area

At the bottom left of the screen you can see the request description area. There are 3 tabs - Headers, Query parameters, and Body, that you can use to edit HTTP headers, query parameters, and request body parameters accordingly.

Let's look at the Headers tab. You can see that it is a table with the following fields:

  • Header name;

  • Header value type (as described above);

  • Description.

All possible standard operations are supported.

The Query Parameters tab is used for editing query parameters, and it is functually identical to the Headers tab.

As mentioned before, in an ApiRoute node you can describe several bodies for a single request. For example, a single endpoint can take the data both with the application/json and application/xml Content-Type. There are several different content-type tabs on the Body tab:

In the screenshot you can see the following parts of the interface:

  1. The button that edits the current content-type value. If you click on it, you'll see a text box instead, where you can enter your content-type value.

  2. Delete the request body button.

  3. Add the request body button.

  4. The current content-type of the node.

  5. The request body editing area.

The request body editing area changes according to the content-type value: if the content-type isapplication/x-www-form-urlencoded ormultipart/form-data, then the editing area looks like a table (like in the Headers tab), otherwise it has the text representation like in the screenshot above. The description format is OpenAPI in this case.

Request parameters description area

There is a response editing panel at the bottom right of the ApiRoute tab interface. As mentioned before, TestMace allows you to describe several responses for a single endpoint. Look at the interface:

There is a separate tab for each response. On these tabs you can edit response codes, descriptions, and even response HTTP headers and bodies. The interface is similar to ones in the request area.

Integration with RequestStep nodes

TestMace provides integration with ApiRoute nodes in RequestStep nodes. The integration is implemented in autocompletion of URLs, HTTP headers, query parameters, RequestStep nodes' request body parameters. Autocompletion works for all ApiRoute nodes URLs, but for other parameters the following algorithm is applied:

  • Take the RequestStep node method and URL;

  • Find all ApiRoute nodes with this method and URL;

  • Run the specified parameter (e. g. an HTTP header) search among the ApiRoute nodes.

File Representation

An ApiRoute node is a folder with the node name, containing the index.yml file with the following format:

{
  "type": "object",
  "properties": {
    "type": {
      "description": "Type of ApiRoute node",
      "const": "ApiRoute",
      "type": "string"
    },
    "url": {
      "type": "string",
      "default": ""
    },
    "method": {
      "$ref": "#/definitions/RequestMethod"
    },
    "description": {
      "type": "string",
      "default": ""
    },
    "requests": {
      "$ref": "#/definitions/ApiRequests",
      "description": "List of requests"
    },
    "responses": {
      "description": "List of responses",
      "type": "array",
      "items": {
        "$ref": "#/definitions/ResponseParameters"
      },
      "default": []
    },
    "children": {
      "description": "List of children names",
      "type": "array",
      "items": {
        "type": "string"
      },
      "default": []
    },
    "variables": {
      "$ref": "#/definitions/NodeVariables",
      "description": "Node variables dictionary"
    },
    "name": {
      "description": "Node name",
      "type": "string"
    }
  },
  "required": [
    "children",
    "description",
    "method",
    "name",
    "requests",
    "responses",
    "type",
    "url",
    "variables"
  ],
  "definitions": {
    "RequestMethod": {
      "enum": [
        "DELETE",
        "GET",
        "OPTIONS",
        "PATCH",
        "POST",
        "PUT"
      ],
      "type": "string"
    },
    "ApiRequests": {
      "type": "object",
      "properties": {
        "queryParameters": {
          "description": "List of query parameters",
          "type": "array",
          "items": {
            "$ref": "#/definitions/QueryParameter"
          }
        },
        "headers": {
          "description": "List of headers",
          "type": "array",
          "items": {
            "$ref": "#/definitions/QueryParameter"
          }
        },
        "cookies": {
          "description": "List of cookies",
          "type": "array",
          "items": {
            "$ref": "#/definitions/QueryParameter"
          }
        },
        "bodies": {
          "description": "List of bodies",
          "type": "array",
          "items": {
            "$ref": "#/definitions/RequestParameters"
          },
          "default": []
        }
      },
      "required": [
        "bodies",
        "cookies",
        "headers",
        "queryParameters"
      ]
    },
    "QueryParameter": {
      "type": "object",
      "properties": {
        "name": {
          "type": "string"
        },
        "type": {
          "enum": [
            "array",
            "boolean",
            "integer",
            "number",
            "object",
            "string"
          ],
          "type": "string"
        },
        "description": {
          "type": "string"
        }
      },
      "required": [
        "name",
        "type"
      ]
    },
    "RequestParameters": {
      "type": "object",
      "properties": {
        "contentType": {
          "type": "string"
        },
        "schema": {
          "anyOf": [
            {
              "$ref": "#/definitions/SchemaRef"
            },
            {
              "$ref": "#/definitions/OneOf"
            },
            {
              "$ref": "#/definitions/AllOf"
            },
            {
              "$ref": "#/definitions/AnyOf"
            },
            {
              "$ref": "#/definitions/ObjectMember"
            },
            {
              "$ref": "#/definitions/ArrayMember"
            },
            {
              "$ref": "#/definitions/ScalarMember"
            }
          ]
        }
      },
      "required": [
        "contentType",
        "schema"
      ]
    },
    "SchemaRef": {
      "type": "object",
      "properties": {
        "$ref": {
          "type": "string"
        }
      },
      "required": [
        "$ref"
      ]
    },
    "OneOf": {
      "type": "object",
      "properties": {
        "oneOf": {
          "type": "array",
          "items": {
            "anyOf": [
              {
                "$ref": "#/definitions/SchemaRef"
              },
              {
                "$ref": "#/definitions/OneOf"
              },
              {
                "$ref": "#/definitions/AllOf"
              },
              {
                "$ref": "#/definitions/AnyOf"
              },
              {
                "$ref": "#/definitions/ObjectMember"
              },
              {
                "$ref": "#/definitions/ArrayMember"
              },
              {
                "$ref": "#/definitions/ScalarMember"
              }
            ]
          }
        }
      },
      "required": [
        "oneOf"
      ]
    },
    "AllOf": {
      "type": "object",
      "properties": {
        "allOf": {
          "type": "array",
          "items": {
            "anyOf": [
              {
                "$ref": "#/definitions/SchemaRef"
              },
              {
                "$ref": "#/definitions/OneOf"
              },
              {
                "$ref": "#/definitions/AllOf"
              },
              {
                "$ref": "#/definitions/AnyOf"
              },
              {
                "$ref": "#/definitions/ObjectMember"
              },
              {
                "$ref": "#/definitions/ArrayMember"
              },
              {
                "$ref": "#/definitions/ScalarMember"
              }
            ]
          }
        }
      },
      "required": [
        "allOf"
      ]
    },
    "AnyOf": {
      "type": "object",
      "properties": {
        "anyOf": {
          "type": "array",
          "items": {
            "anyOf": [
              {
                "$ref": "#/definitions/SchemaRef"
              },
              {
                "$ref": "#/definitions/OneOf"
              },
              {
                "$ref": "#/definitions/AllOf"
              },
              {
                "$ref": "#/definitions/AnyOf"
              },
              {
                "$ref": "#/definitions/ObjectMember"
              },
              {
                "$ref": "#/definitions/ArrayMember"
              },
              {
                "$ref": "#/definitions/ScalarMember"
              }
            ]
          }
        }
      },
      "required": [
        "anyOf"
      ]
    },
    "ObjectMember": {
      "type": "object",
      "properties": {
        "type": {
          "type": "string",
          "enum": [
            "object"
          ]
        },
        "properties": {
          "$ref": "#/definitions/SchemaMember"
        },
        "required": {
          "type": "boolean"
        },
        "additionalProperties": {
          "$ref": "#/definitions/ScalarMember"
        },
        "description": {
          "type": "string"
        }
      },
      "required": [
        "type"
      ]
    },
    "SchemaMember": {
      "type": "object",
      "additionalProperties": {
        "anyOf": [
          {
            "$ref": "#/definitions/SchemaRef"
          },
          {
            "$ref": "#/definitions/OneOf"
          },
          {
            "$ref": "#/definitions/AllOf"
          },
          {
            "$ref": "#/definitions/AnyOf"
          },
          {
            "$ref": "#/definitions/ObjectMember"
          },
          {
            "$ref": "#/definitions/ArrayMember"
          },
          {
            "$ref": "#/definitions/ScalarMember"
          }
        ]
      }
    },
    "ArrayMember": {
      "type": "object",
      "properties": {
        "type": {
          "type": "string",
          "enum": [
            "array"
          ]
        },
        "items": {
          "anyOf": [
            {
              "$ref": "#/definitions/SchemaRef"
            },
            {
              "$ref": "#/definitions/OneOf"
            },
            {
              "$ref": "#/definitions/AllOf"
            },
            {
              "$ref": "#/definitions/AnyOf"
            },
            {
              "$ref": "#/definitions/ObjectMember"
            },
            {
              "$ref": "#/definitions/ArrayMember"
            },
            {
              "$ref": "#/definitions/ScalarMember"
            }
          ]
        },
        "description": {
          "type": "string"
        }
      },
      "required": [
        "items",
        "type"
      ]
    },
    "ScalarMember": {
      "type": "object",
      "properties": {
        "type": {
          "$ref": "#/definitions/ScalarSchemaType"
        },
        "description": {
          "type": "string"
        }
      },
      "required": [
        "type"
      ]
    },
    "ScalarSchemaType": {
      "enum": [
        "boolean",
        "integer",
        "number",
        "string"
      ],
      "type": "string"
    },
    "ResponseParameters": {
      "type": "object",
      "properties": {
        "code": {
          "description": "Http-code (e.g. 200, 404)",
          "type": "string"
        },
        "description": {
          "type": "string"
        },
        "headers": {
          "type": "array",
          "items": {
            "$ref": "#/definitions/QueryParameter"
          }
        },
        "content": {
          "$ref": "#/definitions/RequestParameters",
          "description": "Response body"
        }
      },
      "required": [
        "code",
        "content"
      ]
    },
    "NodeVariables": {
      "type": "object",
      "additionalProperties": {
        "type": "string"
      }
    }
  },
  "$schema": "http://json-schema.org/draft-07/schema#"
}

Last updated