Mocking POST JSON Requests with Moco: A Custom JsonExtractor Guide

When using Moco API for request virtualization, the default extractor cannot handle POST JSON bodies, so this article shows how to implement a custom JsonExtractor in Java and use Groovy matchers to verify JSON parameters effectively.

FunTester
FunTester
FunTester
Mocking POST JSON Requests with Moco: A Custom JsonExtractor Guide

Problem with Moco's ParamRequestExtractor

When using the Moco framework to virtualize APIs, the built‑in ParamRequestExtractor can extract values from URL query parameters but it cannot read a JSON payload sent in a POST request. The extractor calls request.getQueries(), which only returns the query string, so any JSON body is ignored and the extraction result is null.

Custom JsonExtractor implementation

The following Java class reads the raw request content, parses it as JSON with net.sf.json.JSONObject, extracts the value for a specified key, and returns the value as a one‑element String[]. It also provides a static factory method queryJson that validates the key before creating the extractor.

package com.fun.moco.support;

import com.github.dreamhead.moco.HttpRequest;
import com.github.dreamhead.moco.HttpRequestExtractor;
import com.github.dreamhead.moco.RequestExtractor;
import com.google.common.base.Optional;
import net.sf.json.JSONObject;
import static com.github.dreamhead.moco.util.Preconditions.checkNotNullOrEmpty;
import static com.google.common.base.Optional.fromNullable;

/** Extracts a value from a JSON request body */
@SuppressWarnings("all")
public class JsonExtractor extends HttpRequestExtractor<String[]> {
    private final String param;

    public JsonExtractor(final String param) {
        this.param = param;
    }

    @Override
    protected Optional<String[]> doExtract(HttpRequest request) {
        try {
            String body = request.getContent().toString();
            String value = JSONObject.fromObject(body).getString(param);
            return fromNullable(new String[]{value});
        } catch (Exception e) {
            // Return an empty string when the key is missing or parsing fails
            return fromNullable(new String[]{""});
        }
    }

    /**
     * Factory method used in test scripts.
     *
     * @param param the JSON key to extract; must not be empty
     * @return a <code>RequestExtractor<String[]></code> for the given key
     */
    public static RequestExtractor<String[]> queryJson(final String param) {
        return new JsonExtractor(checkNotNullOrEmpty(param, "Parameter cannot be empty!"));
    }
}

By calling request.getContent() the extractor obtains the raw POST body, converts it to a JSON object, and retrieves the desired field. If parsing fails, it safely returns an empty string to avoid NullPointerException in downstream matchers.

Groovy matcher helpers for concise assertions

In Groovy test scripts the following static methods wrap Moco matchers, allowing developers to compare either query‑string parameters or JSON body fields with expected values.

/** Compare a GET query parameter */
static RequestMatcher eqArgs(String key, String value) {
    eq query(key), value
}

/** Compare a POST JSON field */
static RequestMatcher eqParams(String key, String value) {
    eq queryJson(key), value
}

Usage example (Groovy):

import static com.fun.moco.support.JsonExtractor.queryJson
import static com.github.dreamhead.moco.Moco.*

// Verify a GET request
request(eqArgs("id", "123"))

// Verify a POST request with JSON body
request(eqParams("username", "alice"))

These helpers rely on the custom JsonExtractor and make test code more readable while keeping the verification logic within Moco's fluent API.

Original Source

Signed-in readers can open the original source through BestHub's protected redirect.

Sign in to view source
Republication Notice

This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactadmin@besthub.devand we will review it promptly.

JavatestingJSONGroovyMoCoAPI mocking
FunTester
Written by

FunTester

10k followers, 1k articles | completely useless

0 followers
Reader feedback

How this landed with the community

Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.