javahttppostfastapi

Java POST to Python FastApi - JSON payload - Unprocessable entity?


I'm attempting to make a POST request to a FastApi from a Java front-end. I have tried several different things I have found reading online, but I cannot make it work.

Java implementation:

public JSONObject saveData(JSONObject data) {
    JSONObject jsonResponse;
    try {
        HttpClient client = newHttpClient();

        HttpRequest request = HttpRequest.newBuilder(URI.create(apiUrl + "save_variants"))
                .version(HttpClient.Version.HTTP_2)
                .header("accept", "application/json")
                .POST(HttpRequest.BodyPublishers.ofString(data.toString()))
                .build();

        HttpResponse<String> response =
                client.send(request, HttpResponse.BodyHandlers.ofString());

        String jsonString = response.body().replaceAll("\\\\","");
        jsonResponse = new JSONObject(jsonString);
    } catch (Exception e) {
        throw new RuntimeException(e);
    }

    System.out.println("Received updated data:" + jsonResponse);

    return jsonResponse;
}

Python FastApi post:

class Item(BaseModel):
    item: str


@app.post("/variants")
async def save_variants(item: Item):
    logger.info(f"Payload:${item}")

    return read_param_json("variant_parameters_original.json")

On FastApi side: enter image description here

I can't seem to get the correct data passed to FastApi, or get FastApi to read it correctly - unsure where the problem is exactly.

I tried this: How to make a JSON POST request from Java client to Python FastAPI server?, same error

EDIT: Request response:

Received updated data:{"detail":[{"msg":"Field required","loc":["body"],"input":null,"type":"missing"}]}


Solution

  • So I wrote a basic example from the post mentioned in the question and it worked (Java POST to Python FastApi - JSON payload - Unprocessable entity?)

    I realised that the item has a member item, who's value needs to be the payload I am sending.

    Solved by:

    In Java:

    jsonInputString = "{\"payload\": \"" + jsonInputString + "\"}";
    

    In the Python:

    class User(BaseModel):
        payload: str
    
    
    @app.post("/variants")
    def main(user: User):
        json_obj = json.loads(user.payload)
        logger.warning(f"Received:${json_obj}")
    
        with open("variant_parameters.json", "w") as f:
            f.write(json.dumps(json_obj))