Mock Server API Definition
APIGIT offers a programmable and dynamic MockServer, powered by Express.js and running in a Node.js sandbox container within the APIGIT cloud. This robust tool allows you to simulate complex business logic with dynamic content or persistent states, enabling you to test your APIs in a realistic environment without requiring an actual backend.With the power of Express.js, MockServer provides flexibility in defining routes, using middleware, and creating intricate responses—all with familiar JavaScript conventions. Additionally, MockServers can be automatically generated from your API specifications with just one click, making setup effortless. By using MockServer, you can quickly validate your APIs, identify issues, and ensure correct functionality before deployment, ultimately saving significant time and effort during development.
DEFINE API
mock.define(path, method, callback)
The mock.define() method configures HTTP routes. The following snippet illustrates the simplest route definition possible. Mock Server translates the path strings to regular expressions, used internally to match incoming requests. Query strings are not considered when performing these matches, for example "GET /" would match the following route, as would "GET /?user=bob".
mock.define("/", "GET", function(req, res) {
res.send("Hello world");
})
The callback is always passed a Request object and a Response object. Route parameters can be specified using {param_name}
in paths. For example, if you have a route /user/{name}
, then the "name" property is available to you as req.params.name.
mock.define("/user/:name", "get", function(req, res) {
res.send("Hello " + req.params.name);
})
Its important to note that all mock.define() blocks must end with a call to send a response such as res.send(). Without this call your service will timeout and not return a successful result. See the Response section for more details.
MIDDLEWARE
mock.use()
The mock.use() is used to add middleware, which is exactly a wrapper of expressjs middleware using.
function mw1(req, res, next) {
console.log("This is a middleware example1");
next();
}
function mw2(req, res, next) {
console.log("This is a middleware example2");
next();
}
function mw3(req, res, next) {
console.log("This is a middleware example3");
next();
}
mock.use(mw1);
mock.use(mw2, mw3);
// Define middleware for a specific path
mock.use('/specific-path', (req, res, next) => {
console.log('Middleware triggered for /specific-path');
next(); // Pass control to the next middleware/route handler
});
Request
The req object represents the request message and has properties for the request query string, parameters, body, HTTP headers, and so on. In this documentation and by convention, the object is always referred to as req (and the response message is res) but its actual name is determined by the parameters to the callback function in which you’re working.
PROPERTIES
req.params
This property is an array containing property names mapped to named route "parameters", defaults to {}
. For example, if you have a route /user/:name
then the "name" property is available to you at req.params.name
mock.define('/repository/:user/:repo', 'GET', (req, res) => {
// Access route parameters from req.params
const { user, repo } = req.params;
// Respond with the extracted parameters
res.json({
message: 'Repository Details',
user: user,
repo: repo
});
});
req.query
This property is an object containing the parsed query string, defaults to {}
.
mock.define('/search', 'GET', (req, res) => {
// Access query parameters from req.query
const { keyword, page, limit } = req.query;
// Respond with the received query parameters
res.json({
message: 'Query Parameters Received',
keyword: keyword || 'none', // Default value if not provided
page: page ? parseInt(page, 10) : 1, // Default to page 1
limit: limit ? parseInt(limit, 10) : 10 // Default to 10 items per page
});
});
req.body
This property is an object containing the parsed request body, defaults to {}
. The body will be parsed based on the "Content-Type" header.
// Route to handle POST {"name":"john", age:50}
mock.define('/user', 'POST', (req, res) => {
// Access properties from req.body
const name = req.body.name; // Extract name
const age = req.body.age; // Extract age
// Respond with the parsed body data
res.json({
message: 'User Data Received',
name: name,
age: age
});
});
req.cookies
This property is an object that contains the parsed cookies sent by the user-agent
mock.define('/get-cookies', 'GET', (req, res) => {
// Access all cookies
const allCookies = req.cookies;
// Extract specific cookies
const username = req.cookies.username || 'Guest'; // Default to 'Guest' if not set
const sessionId = req.cookies.session_id || 'No Session';
const theme = req.cookies.theme || 'Default Theme';
// Send detailed cookie information
res.json({
message: 'Detailed Cookie Information Retrieved',
cookies: {
username: username,
session_id: sessionId,
theme: theme
},
allCookies: allCookies // Include all cookies for debugging purposes
});
});
// Route to set cookies (for testing purposes)
mock.define('/set-cookies', 'GET', (req, res) => {
// Set some sample cookies
res.cookie('username', 'john_doe', { httpOnly: true });
res.cookie('session_id', 'abc123', { secure: true });
res.cookie('theme', 'dark');
res.send('Sample cookies have been set!');
});
req.originalUrl and req.path
This property returns the original request URL and path.
// Route to demonstrate req.originalUrl and req.path
mock.define('/user/:username', 'GET', (req, res) => {
// Extract URL and path
const originalUrl = req.originalUrl; // Full URL with query string
const path = req.path; // Path without query string
// Respond with details
res.json({
message: 'Path and URL Details',
originalUrl: originalUrl,
path: path,
});
});
req.ip
This property returns the originating IP address of the request
mock.define('/check-content-type', 'POST', (req, res) => {
req.ip //= the ip of client, like 10.100.12.10
...
});
METHODS
req.get(field)
This function returns the case-insensitive request header for field.
// get headers from req by req.get(header-name)
mock.define('/headers', 'POST', (req, res) => {
// Retrieve headers using req.get()
const contentType = req.get('Content-Type'); // Retrieves the Content-Type header
const contentLength = req.get('Content-Length'); // Retrieves the Content-Length header
// Respond with the retrieved headers
res.json({
message: 'Header Information Retrieved',
headers: {
"Content-Type": contentType,
"Content-Length": contentLength
}
});
});
req.is(type)
Check if the incoming request matches the given mime type. If "Content-Type" header field isn't present on the request, it will return false
// check content type by req.is(type)
mock.define('/check-content-type', 'POST', (req, res) => {
// Check Content-Type of the request
// With Content-Type: text/html; charset=utf-8
req.is('html')
// => 'html'
req.is('text/html')
// => 'text/html'
req.is('text/*')
// => 'text/*'
// When Content-Type is application/json
req.is('json')
// => 'json'
req.is('application/json')
// => 'application/json'
req.is('application/*')
// => 'application/*'
req.is('html')
// => false
...
});
Response
The res object represents the response message that Mock Server sends in response to a request message. Use the res object to set response heaers, status codes and more. In this documentation and by convention, the object is always referred to as res (and the request message is req) but its actual name is determined by the parameters to the callback function in which you’re working.
METHODS
res.status(code)
Sets the response status. If you dont set a status, a successful result will default to a 200 status
// set status code by calling res.status(code)
mock.define('/not-found', 'GET', (req, res) => {
res.status(404).json({
message: 'Resource not found',
code: 404
});
});
// Generic route
mock.define('/', 'GET', (req, res) => {
res.status(200).send('Welcome to the Express server!');
});
res.set(field, [value])
Sets a response header. Sets header field to value where value is a string or an Array of strings. Alternatively, pass in a single argument of type object
// Route to set a single header
mock.define('/single-header', 'GET', (req, res) => {
res.set('Content-Type', 'application/json'); // Set Content-Type header
res.set('X-Header', ['hello', '123']); // Set a custom header with multiple values
res.json({ message: 'Single header set!' }); // Respond with JSON
});
// Route to set multiple headers
mock.define('/multiple-headers', 'GET', (req, res) => {
res.set({
'Content-Type': 'application/json', // Set Content-Type
'Content-Length': '100', // Set Content-Length
'X-Custom-Header': 'CustomValue' // Set a custom header
});
res.json({ message: 'Multiple headers set!' }); // Respond with JSON
});
res.get(field)
Gets the case-insensitive response header for field.
mock.define('/get-res-header', 'GET', (req, res) => {
res.get("Content-Type")
// = "application/json"
res.get("content-type")
// = "application/json"
...
});
res.type(type)
Sets the Content-Type to the mime lookup of type.
// set content type by calling res.type(type)
mock.define('/html', 'GET', (req, res) => {
res.type('html'); // Sets Content-Type to text/html
res.send('<h1>This is an HTML response</h1>');
});
// Route to set Content-Type to JSON (shorthand)
mock.define('/json', 'GET', (req, res) => {
res.type('json'); // Sets Content-Type to application/json
res.send({ message: 'This is a JSON response' });
});
// Route to set Content-Type to application/json explicitly
mock.define('/application-json', 'GET', (req, res) => {
res.type('application/json'); // Sets Content-Type to application/json
res.send({ message: 'Explicit application/json response' });
});
res.send(body)
Sends a response.
// Route to send a plain text response
mock.define('/text', 'GET', (req, res) => {
res.send('Hello, this is a plain text response!');
});
// Route to send an HTML response
mock.define('/html', 'GET', (req, res) => {
res.send('<h1>This is an HTML response</h1>');
});
// Route to send a JSON response
mock.define('/json', 'GET', (req, res) => {
res.send({ message: 'This is a JSON response', status: 'success' });
});
// Route to send a Buffer response
mock.define('/buffer', 'GET', (req, res) => {
const buffer = Buffer.from('This is a buffer response', 'utf-8');
res.send(buffer);
});
// Route to send a status code and response together
mock.define('/status', 'GET', (req, res) => {
res.status(200).send('Everything is okay!');
});
If a Content-Type hasnt been set this function will parse the data and set the appropriate header. For example, if you pass in an object then the Content-Type will be set to 'application/json'. When a String is provided the Content-Type is set to 'text/html'. When a Number is provided without a body then a response body string is assigned for you. For example, 200 will respond with the text 'OK'.
Calling this function will also complete execution of your service. Further calls to functions will have no effect.
res.json
Sends a json response. This method is identical to res.send() when an object or array is passed however it will also convert non-objects, such as null, into JSON representation.
res.json(null);
res.json({ name: 'bob' });
res.status(404).json({ error: 'Not found' });
res.render(template, [locals])
Renders the response using a Liquid template and sends the rendered result. The template parameter must correspond to a template files in the applications /templates directory without the file extension. For example, /templates/users.liquid template is referenced by its name 'users':
res.render('users', { name: 'bob' });
res.render('canned_response');
Locals can be passed in and must be an Object or Array. These are then made available to the template as res.locals. In the above example, 'name' would be available at res.name.