Group Abstract Group Abstract

Message Boards Message Boards

0
|
2.1K Views
|
1 Reply
|
0 Total Likes
View groups...
Share
Share this post:

Problem setting up an `APIFunction` to receive web form as JSON

Posted 1 year ago

Created the following API Function and trying to test it before deployment:

APIFunction[
{
"checkin"->"RawJSON",
"user"->"RawJSON",
"secret"->"String"
},
DatabinAdd[Databin["xxxxxxx"],<|
"Timestamp"->FromUnixTime[#checkin[["createdAt"]]],
"CheckinID"->#checkin[["id"]],
"Venue"->#checkin[["venue","name"]],
"Category"->#checkin[["venue","categories",1,"name"]],
"Location"->GeoPosition[{#checkin[["venue","location","lat"]],#checkin[["venue","location","lng"]]}],
"Shout"->#checkin[["shout"]]
|>
&]
,
"HTMLThemed"
]

The resulting item in the datadrop, though, is the top item in the attached list (the datadrop website only returns images, not text):

enter image description here

POSTED BY: Steven Buehler
Posted 1 month ago

Steven,

The core of the issue lies in how the APIFunction extracts the raw body content, and how you are trying to access the elements within the function body.

Solution

CloudDeploy[
 APIFunction[
  (* 1. Specify the function takes raw data and a secret string *)
  { "secret" -> "String" }, 

  (* The main function body: # is the input Association *)
  Module[{json, data},

    (* 2. Extract and decode the raw body content from the request *)
    (* This assumes the JSON is in the request body as text *)
    json = URLDecode[#\[RawData]];

    (* 3. Import the JSON text into a Wolfram Language Association *)
    data = ImportString[json, "JSON"];

    (* 4. Extract the nested 'checkin' data and perform the DatabinAdd *)
    If[AssociationQ[data] && KeyExistsQ[data, "checkin"],
      DatabinAdd[
        Databin["xxxxxxx"], (* Your Databin ID *)
        <| 
          "Timestamp" -> FromUnixTime[data["checkin", "createdAt"]],
          "CheckinID" -> data["checkin", "id"],
          "Venue" -> data["checkin", "venue", "name"],
          "Category" -> data["checkin", "venue", "categories", 1, "name"],
          "Location" -> GeoPosition[{data["checkin", "venue", "location", "lat"], data["checkin", "venue", "location", "lng"]}],
          "Shout" -> data["checkin", "shout"]
        |> 
      ],
      "Error: JSON input format incorrect."
    ]
  ], 
  "HTMLThemed" 
 ]
]

Explanation of Changes

Removed "RawJSON" Specification:

We simplified the parameter specification to only handle the secret as a string. The checkin and user data are accessed via \[RawData].

Accessing the Raw Body (#\[RawData])

When a request is sent, the entire raw body content is available via \[RawData] within the APIFunction's input association (#)

URL Decoding (URLDecode)

Use URLDecode to sanitize and retrieve the plain JSON string.

Parsing JSON (ImportString)

We use ImportString[...,"JSON"] to convert the raw JSON text string into a usable Wolfram Language Association

Accessing Elements (data[...])

Now that data is a full Wolfram Language association representing the JSON structure, you access its elements using standard association key-value syntax (e.g., data["checkin", "id"]). This is much cleaner than the #checkin notation which isn't designed for this use case.

This structure allows the function to correctly receive the JSON payload, parse it into an accessible structure, and then use the nested fields to correctly add data to your Databin.

POSTED BY: Rob Pacey
Reply to this discussion
Community posts can be styled and formatted using the Markdown syntax.
Reply Preview
Attachments
Remove
or Discard