This might be me sucking at C++, but I’m stumped here.
First issue: If I make a request via HttpClient, the response.body only gets ~500 characters, even though the JSON I’m fetching is more like ~1500 characters long.
Second issue: I convert that to a char array, and I only get 10 characters, regardless of what I set the length to. (Unless I set it to less than 10, anyways.)
Third issue: if I hard code the JSON string, the conversion to a char array works as expected and I can parse the JSON… but I still don’t get the value I’m expecting, so I’m just buggered all around.
Here’s my complete code, except I removed the base64’d username and password from the Authorization header:
#include "HttpClient/HttpClient.h"
#include "SparkJson/SparkJson.h"
#include "Adafruit_mfGFX/Adafruit_mfGFX.h"
#include "Adafruit_SSD1351_Photon/Adafruit_SSD1351_Photon.h"
// OLED - You can use any (4 or) 5 pins
#define sclk A3
#define mosi A5
#define dc D7
#define cs A2
#define rst D5
// Color definitions
#define BLACK 0x0000
#define BLUE 0x001F
#define RED 0xF800
#define GREEN 0x07E0
#define CYAN 0x07FF
#define MAGENTA 0xF81F
#define YELLOW 0xFFE0
#define WHITE 0xFFFF
// Option 1: Hardware SPI - uses some analog pins, but much faster
Adafruit_SSD1351 tft = Adafruit_SSD1351(cs, dc, rst);
// Option 2: Software SPI - use any pins but a little slower
//Adafruit_SSD1351 tft = Adafruit_SSD1351(cs, dc, mosi, sclk, rst);
HttpClient http;
// Headers currently need to be set at init, useful for API keys etc.
http_header_t headers[] = {
// { "Content-Type", "application/json" },
{ "Authorization", "Basic <snip>" }, // base64encode(username:password)
{ "Accept" , "application/json" },
{ NULL, NULL } // NOTE: Always terminate headers will NULL
};
http_request_t request;
http_response_t response;
void setup(void) {
tft.begin();
tft.fillScreen(BLACK);
tft.setCursor(0,0);
tft.setTextSize(0);
tft.setTextColor(WHITE);
// http://twcservice.mybluemix.net/api/weather/v2/observations/current?units=e&geocode=40.0388067%2C-84.3428471&language=en-US
request.hostname = "twcservice.mybluemix.net";
request.port = 80;
request.path = "/api/weather/v2/observations/current?units=e&geocode=40.0388067%2C-84.3428471&language=en-US";
//request.body = "{\"key\":\"value\"}";
http.get(request, response, headers);
tft.print("Status: ");
tft.println(response.status);
//response.body = "{\"metadata\":{\"language\":\"en-US\",\"transaction_id\":\"1460309558940:-660053703\",\"version\":\"1\",\"latitude\":40.04,\"longitude\":-84.34,\"units\":\"e\",\"expire_time_gmt\":1460310025,\"status_code\":200},\"observation\":{\"class\":\"observation\",\"expire_time_gmt\":1460310025,\"obs_time\":1460307900,\"obs_time_local\":\"2016-04-10T13:05:00-0400\",\"wdir\":160,\"icon_code\":26,\"icon_extd\":2690,\"sunrise\":\"2016-04-10T07:06:23-0400\",\"sunset\":\"2016-04-10T20:11:13-0400\",\"day_ind\":\"D\",\"uv_index\":3,\"uv_warning\":0,\"wxman\":\"wx4400\",\"obs_qualifier_code\":null,\"ptend_code\":2,\"dow\":\"Sunday\",\"wdir_cardinal\":\"SSE\",\"uv_desc\":\"Moderate\",\"phrase_12char\":\"Cloudy/Wind\",\"phrase_22char\":\"Cloudy/Wind\",\"phrase_32char\":\"Cloudy/Wind\",\"ptend_desc\":\"Falling\",\"sky_cover\":\"Cloudy\",\"clds\":\"OVC\",\"obs_qualifier_severity\":null,\"vocal_key\":\"OT48:OX2690\",\"imperial\":{\"wspd\":20,\"gust\":24,\"vis\":10.000,\"mslp\":1018.7,\"altimeter\":30.09,\"temp\":48,\"dewpt\":27,\"rh\":43,\"wc\":41,\"hi\":48,\"temp_change_24hour\":11,\"temp_max_24hour\":44,\"temp_min_24hour\":27,\"pchange\":-0.10,\"feels_like\":41,\"snow_1hour\":0.0,\"snow_6hour\":0.0,\"snow_24hour\":0.0,\"snow_mtd\":1.2,\"snow_season\":21.3,\"snow_ytd\":21.3,\"snow_2day\":0.7,\"snow_3day\":0.8,\"snow_7day\":0.9,\"ceiling\":7400,\"precip_1hour\":0.00,\"precip_6hour\":0.00,\"precip_24hour\":0.00,\"precip_mtd\":1.10,\"precip_ytd\":11.76,\"precip_2day\":0.29,\"precip_3day\":0.30,\"precip_7day\":0.96,\"obs_qualifier_100char\":null,\"obs_qualifier_50char\":null,\"obs_qualifier_32char\":null}}}";
int str_len = response.body.length() + 1;
tft.print("Length: "); tft.println(str_len);
char char_array[str_len];
response.body.toCharArray(char_array, str_len);
DynamicJsonBuffer jsonBuffer;
JsonObject& root = jsonBuffer.parseObject(char_array);
if (root.success()) {
tft.print("Current Temperature: ");
const char* temp = root["observation"]["imperial"]["temp"];
tft.println(temp);
} else {
tft.setTextColor(RED);
tft.println("parseObject() failed");
tft.setTextColor(GREEN);
uint32_t freemem = System.freeMemory();
tft.print("Free memory: ");
tft.print(freemem/1024);
tft.println("k");
tft.setTextColor(WHITE);
tft.println(char_array);
tft.setTextColor(CYAN);
tft.println(response.body);
}
}
void loop() {
}
The actual printout on the screen is something like
Status: 200
Length: 501
parseObject() failed
Free memory: 59k
{"metadata
{"metadata":{"language":"en-US","transaction_id":"1460309558940:-660053703","version":"1","latitude":40.04,"longitude":-84.34,"units":"e","expire_time_gmt":1460310025,"status_code":200},"observation":{"class":"observation","expire_
Or, with the hard coded response.body:
Status: 200
Length: 1423
Temp:
Finally, here’s an example of the JSON response I’m trying to parse:
{"metadata":{"language":"en-US","transaction_id":"1460309558940:-660053703","version":"1","latitude":40.04,"longitude":-84.34,"units":"e","expire_time_gmt":1460310025,"status_code":200},"observation":{"class":"observation","expire_time_gmt":1460310025,"obs_time":1460307900,"obs_time_local":"2016-04-10T13:05:00-0400","wdir":160,"icon_code":26,"icon_extd":2690,"sunrise":"2016-04-10T07:06:23-0400","sunset":"2016-04-10T20:11:13-0400","day_ind":"D","uv_index":3,"uv_warning":0,"wxman":"wx4400","obs_qualifier_code":null,"ptend_code":2,"dow":"Sunday","wdir_cardinal":"SSE","uv_desc":"Moderate","phrase_12char":"Cloudy/Wind","phrase_22char":"Cloudy/Wind","phrase_32char":"Cloudy/Wind","ptend_desc":"Falling","sky_cover":"Cloudy","clds":"OVC","obs_qualifier_severity":null,"vocal_key":"OT48:OX2690","imperial":{"wspd":20,"gust":24,"vis":10.000,"mslp":1018.7,"altimeter":30.09,"temp":48,"dewpt":27,"rh":43,"wc":41,"hi":48,"temp_change_24hour":11,"temp_max_24hour":44,"temp_min_24hour":27,"pchange":-0.10,"feels_like":41,"snow_1hour":0.0,"snow_6hour":0.0,"snow_24hour":0.0,"snow_mtd":1.2,"snow_season":21.3,"snow_ytd":21.3,"snow_2day":0.7,"snow_3day":0.8,"snow_7day":0.9,"ceiling":7400,"precip_1hour":0.00,"precip_6hour":0.00,"precip_24hour":0.00,"precip_mtd":1.10,"precip_ytd":11.76,"precip_2day":0.29,"precip_3day":0.30,"precip_7day":0.96,"obs_qualifier_100char":null,"obs_qualifier_50char":null,"obs_qualifier_32char":null}}}
Any idea what’s going on?