Skip to content

JSON API Page (JAPI)

The JSON API page (aka JAPI) is a runtime JSON API that provides a consolidated template for the handling of various custom functionality throughout the store and allows for a uniform web request/response schema.

Some common use case examples include:

  • Loading product variant data
  • Processing marketing feeds
  • Sending Google recaptcha requests
  • Triggering emails

Requests

All requests to JAPI are required to have the function property set in the JSON request body. The value of the function property controls which block of code to run within the page template. The Content-Type header should be set to application/json on each request to JAPI as well.

Additional properties in the JSON request body will vary and is up to the developer to decide what data needs to be provided in the request to be consumed in the block of code that the function property is targeting.

For example, a request to load product variant data will look similar to the following:

POST /japi HTTP/1.1
Content-Type: application/json
Host: www.example.com

{
"function": "variant-product-data",
"product_code": "prod_variant",
"variant_id": "32799"
}

This example has a function set to target the variant-product-data conditional block in the JAPI page template and is providing a product_code and variant_id to be consumed within the conditional block.

Responses

Responses handled in the JAPI template should follow the schema outlined below for Successful and Unsuccessful responses.

Successful Responses

A successful JAPI response body should contain the following properties:

Name Type Description
success int Integer flag to indicate a successful response - 1.
function string The provided function.
data array object The response body. This will be an array or object depending on the data returned.

For example, a successful response body for processing a feed will look similar to the following:

{
    "data": {
        "count": 1,
        "feeds": [
            {
                "code": "test_feed",
                "config": {
                    "page_code": "TEMPLATEFEED_test_feed",
                    "page_id": 106,
                    "template": "product"
                },
                "eml_attach": "",
                "eml_base64": 0,
                "eml_bcc": "",
                "eml_body": "",
                "eml_cc": "",
                "eml_enbld": 0,
                "eml_from": "",
                "eml_rp_to": "",
                "eml_subj": "",
                "eml_to": "",
                "eml_type": "I",
                "file_enbld": 1,
                "file_loc": "script",
                "file_name": "/feeds/test_feed.csv",
                "id": 1,
                "module_id": 206,
                "name": "Test Feed",
                "uri_acckey": "",
                "uri_enbld": 1
            }
        ],
        "session_id": "7819bbd6980365af4be0e9a677583ac1"
    },
    "function": "process-feed",
    "success": 1
}

The value of the data property will vary and is up to the developer's discretion on what data to return for the targeted function.

Unsuccessful Responses

An unsuccessful JAPI response body should contain the following properties:

Name Type Description
success int Integer flag to indicate a unsuccessful response - 0.
function string The provided function.
error_code string The associated error code.
message string The associated error message.

For example, an unsuccessful response body for processing a feed will look similar to the following:

{
    "error_code": "JAPI-PMF-00002",
    "function": "process-feed",
    "message": "Invalid feed `code` provided.",
    "success": 1
}

It is up to the developer to provide the values of the error_code and message properties for the targeted function.

Page Template

The JAPI page template contains out of the box examples to reference for function conditional blocks and error handling.

HTML Profile Variables

The html_profile item is rendered at the top of the page template and global variables set in the HTML Profile template can be accessed within the conditional functions under the l.html_variables structure. For example, the image placeholders structure set in the HTML Profile template can be accessed in the JAPI page template under l.html_variables:image_placeholders.

Functions

Each custom feature is divided and handled within individual conditional blocks that are targeted by the function property value provided in the request body.

For example, a request body with a function property set to variant-product-data will target the following conditional block in the template:

<mvt:if expr="l.settings:data:function EQ 'variant-product-data'">

A new mvt:if conditional block should be added to the page template for each new additional feature. NOTE that page items may need to be assigned as needed per feature support.

Error Handling

Error handling is up to the developer to implement within each function block. However, it is recommended to use the following format for the error_code value to keep the response schema consistent:

JAPI-{abbreviated function name}-{error number}
  • Abbreviated Function Name: Three characters representing the abbreviated name for the associated function.
  • Error Number: 5 digit error number sequence, where the number increments by 1 for each error. The error numbers have a leading zero.

An example of the first 3 occurrences of error codes within a function block:

JAPI-PMF-00001
JAPI-PMF-00002
JAPI-PMF-00003

Example Functions

Below is a list of common use case functions that can be added to the JAPI page template to quickly add support for the function's features.

Process A Feed

The following function processes a Miva feed via JAPI as an alternative to processing a Miva feed through Miva Scheduled Tasks. This is helpful for setting up a server side request to JAPI to run feeds at specific date/time intervals.

<mvt:comment>
|
|   Process A Feed
|
</mvt:comment>
<mvt:if expr="l.settings:data:function EQ 'process-feed'">
    <mvt:comment>
    |
    |   Error: Feed code not provided
    |
    </mvt:comment>
    <mvt:if expr="l.settings:data:code EQ ''">
        <mvt:assign name="l.response:success"       value="0" />
        <mvt:assign name="l.response:function"      value="l.settings:data:function" />
        <mvt:assign name="l.response:error_code"    value="'JAPI-PMF-00001'" />
        <mvt:assign name="l.response:message"       value="'The feed `code` must be provided.'" />

        <mvt:do file="g.Module_JSON" name="l.JSON_Output_success" value="JSON_Output( l.response )" />
        <mvt:exit />
    </mvt:if>

    <mvt:do file="g.Module_Feature_FDS_DB" name="l.Feed_Load_Code_Success" value="Feed_Load_Code( l.settings:data:code, l.feed ) " />

    <mvt:comment>
    |
    |   Error: Invalid feed code provided
    |
    </mvt:comment>
    <mvt:if expr="NOT l.Feed_Load_Code_Success">
        <mvt:assign name="l.response:success"       value="1" />
        <mvt:assign name="l.response:function"      value="l.settings:data:function" />
        <mvt:assign name="l.response:error_code"    value="'JAPI-PMF-00002'" />
        <mvt:assign name="l.response:message"       value="'Invalid feed `code` provided.'" />

        <mvt:do file="g.Module_JSON" name="l.JSON_Output_success" value="JSON_Output( l.response )" />
        <mvt:exit />
    </mvt:if>

    <mvt:assign name="l.feed_count" value="miva_array_insert_var( l.feeds, l.feed, -1 )" />

    <mvt:do file="g.Module_Feature_FDS_UT" name="l.success" value="Feed_Process_Multiple_ASYNC( l.feeds, l.feed_count, l.session_id )" />

    <mvt:comment>
    |
    |   Set the response object
    |       - success         : 1
    |       - function        : process-feed
    |       - data.count      : Number of feeds processed
    |       - data.feeds      : Array[] of feed objects
    |       - data.session_id : The feed processing session id
    |
    </mvt:comment>
    <mvt:assign name="l.response:success"           value="1" />
    <mvt:assign name="l.response:function"          value="l.settings:data:function" />
    <mvt:assign name="l.response:data:count"        value="l.feed_count" />
    <mvt:assign name="l.response:data:feeds"        value="l.feeds" />
    <mvt:assign name="l.response:data:session_id"   value="l.session_id" />

    <mvt:do file="g.Module_JSON" name="l.JSON_Output_success" value="JSON_Output( l.response )" />
    <mvt:exit />
</mvt:if>

Run A Scheduled Task Trigger

The following function can be used to run a Miva Scheduled Tasks trigger.

<mvt:if expr="l.settings:data:function EQ 'trigger-scheduled-task'">
    <mvt:comment>
    |
    |   Error: Trigger not provided
    |
    </mvt:comment>
    <mvt:if expr="l.settings:data:trigger EQ ''">
        <mvt:assign name="l.response:success"       value="0" />
        <mvt:assign name="l.response:function"      value="l.settings:data:function" />
        <mvt:assign name="l.response:error_code"    value="'JAPI-TST-00001'" />
        <mvt:assign name="l.response:message"       value="'The `trigger` input must be provided.'" />

        <mvt:do file="g.Module_JSON" name="l.JSON_Output_success" value="JSON_Output( l.response )" />
        <mvt:exit />
    </mvt:if>

    <mvt:do file="g.Module_Feature_SCH_UT" name="l.ScheduledTask_Trigger_Success" value="ScheduledTask_Trigger( l.settings:data:trigger )" />

    <mvt:comment>
    |
    |   Error: Invalid trigger
    |
    </mvt:comment>
    <mvt:if expr="NOT l.ScheduledTask_Trigger_Success">
        <mvt:assign name="l.response:success"       value="1" />
        <mvt:assign name="l.response:function"      value="l.settings:data:function" />
        <mvt:assign name="l.response:error_code"    value="'JAPI-TST-00002'" />
        <mvt:assign name="l.response:message"       value="'Issue running scheduled task trigger `' $ l.settings:data:trigger $ '`.'" />

        <mvt:do file="g.Module_JSON" name="l.JSON_Output_success" value="JSON_Output( l.response )" />
        <mvt:exit />
    </mvt:if>

    <mvt:comment>
    |
    |   Set the response object
    |       - success         : 1
    |       - function        : trigger-scheduled-task
    |       - data.results    : l.ScheduledTask_Trigger_Success value
    |
    </mvt:comment>
    <mvt:assign name="l.response:success"           value="1" />
    <mvt:assign name="l.response:function"          value="l.settings:data:function" />
    <mvt:assign name="l.response:data:results"      value="l.ScheduledTask_Trigger_Success" />

    <mvt:do file="g.Module_JSON" name="l.JSON_Output_success" value="JSON_Output( l.response )" />
    <mvt:exit />
</mvt:if>