fast_json/Tests/TestJsonRealWorld.mq5
2026-01-25 23:39:19 -03:00

140 líneas
4,4 KiB
MQL5

//+------------------------------------------------------------------+
//| TestJsonRealWorld.mq5 |
//| AI-Toolkit |
//+------------------------------------------------------------------+
#property script_show_inputs
#include "../fast_json.mqh"
input string InpApiKey =
"sk-proj-A15lldKFDf04mO_Qf8xi22nVEVhizdrN1FRdV-"
"utjN4MtPZelNpc4Udm6MboDCGtbY69m_fQ-"
"BT3BlbkFJbCDOIuUTFoij4La2kiquuwffcW9KQHcK4CezBTF07LvuR6tElHLKTuiNFPPbMOvgD"
"M2DskvO4A"; // OpenAI API Key (Paste here)
input string InpModel = "gpt-4o-mini"; // Model to test
void OnStart() {
Print("=== REAL WORLD JSON TEST: OPENAI API (Native WebRequest) ===");
if (InpApiKey == "") {
Print("ERROR: Please provide an API Key in the inputs.");
return;
}
// Check Allowed URL
if (!TerminalInfoInteger(TERMINAL_DLLS_ALLOWED) &&
MQLInfoInteger(MQL_PROFILER)) {
// Just a hint, but WebRequest needs URL allowed in Options
Print("NOTE: Ensure 'https://api.openai.com' is allowed in "
"Tools->Options->Expert Advisors");
}
// 1. Prepare Request Data using Builder
CJsonBuilder b;
b.Obj()
.Key("model")
.Val(InpModel)
.Key("messages")
.Arr()
.Obj()
.Key("role")
.Val("user")
.Key("content")
.Val("Return a complex JSON with nested arrays and mixed types for "
"testing a parser.")
.EndObj()
.EndArr()
.Key("temperature")
.Val(0.7)
.EndObj();
string body_str = b.Build();
char post_data[];
StringToCharArray(body_str, post_data, 0, WHOLE_ARRAY, CP_UTF8);
// Remove null terminator if present at end for WebRequest? Usually fine, but
// safer to trim
if (ArraySize(post_data) > 0 && post_data[ArraySize(post_data) - 1] == 0)
ArrayResize(post_data, ArraySize(post_data) - 1);
char result_data[];
string result_headers_str;
string headers = "Content-Type: application/json\r\nAuthorization: Bearer " +
InpApiKey + "\r\n";
// 2. Execute Native Request
Print("Sending request to OpenAI...");
ulong t0 = GetMicrosecondCount();
int res_code =
WebRequest("POST", "https://api.openai.com/v1/chat/completions", headers,
10000, post_data, result_data, result_headers_str);
ulong t_net = GetMicrosecondCount() - t0;
Print("Status: ", res_code);
Print("Network Time: ", t_net / 1000, " ms");
if (res_code != 200) {
Print("FAIL: Request failed (Code ", res_code, ")");
if (ArraySize(result_data) > 0)
Print("Body: ", CharArrayToString(result_data));
else
Print("Error: ", GetLastError());
return;
}
string json_response =
CharArrayToString(result_data, 0, WHOLE_ARRAY, CP_UTF8);
Print("Payload Size: ", StringLen(json_response), " bytes");
// 3. Parse Real JSON
Print("\n--- 2. Parsing Real Payload ---");
CJson doc;
t0 = GetMicrosecondCount();
bool success = doc.Parse(json_response);
ulong t_parse = GetMicrosecondCount() - t0;
if (success) {
Print("PASS: Parse successful.");
Print("Parse Time: ", t_parse, " us");
// 4. Data Extraction
if (doc["choices"].IsArray() && doc["choices"].Size() > 0) {
string content = doc["choices"][0]["message"]["content"].ToString();
Print("\nExtracting Content (First 100 chars):");
Print(StringSubstr(content, 0, 100) + "...");
int prompt_tokens = doc["usage"]["prompt_tokens"].ToInt();
int completion_tokens = doc["usage"]["completion_tokens"].ToInt();
int total_tokens = doc["usage"]["total_tokens"].ToInt();
Print("\nUsage Stats:");
Print(" Prompt: ", prompt_tokens);
Print(" Completion: ", completion_tokens);
Print(" Total: ", total_tokens);
if (total_tokens > 0)
Print("PASS: Data extraction verification.");
else
Print("FAIL: Token count is zero.");
} else {
Print("FAIL: 'choices' array missing or empty.");
}
// 5. Pretty Print Log
Print("\n--- 3. Pretty Print Demo ---");
Print(doc.Serialize(true));
} else {
int l, c;
doc.GetErrorPos(l, c);
Print("FAIL: Parse Error ", EnumToString((EnumJsonError)doc.GetLastError()),
" at Line ", l, " Col ", c);
Print("Context: ",
StringSubstr(json_response, doc.GetLastError() > 0 ? 0 : 0, 50));
}
Print("=== TEST COMPLETE ===");
}