I am working in Delphi 10 Sydney.
I have to send a base64 string to an API in JSON format. I have shortened the base64 string for security reasons.
FSignatureData is the base64 string I want to send:
/9j/4AAQSkZJRgABAQAAAQABAAD/..
But what I sent to the API is:
\/9j\/4AAQSkZJRgABAQAAAQABAAD\/..
I have an object:
TJSONSignature = class
private
FSignatureData: string;
published
property SignatureData: string read FSignatureData write FSignatureData;
I add this object as JSON to a JsonArray:
var
myJSONValue: TJSONObject;
begin
myJSONValue := TJSON.ObjectToJsonObject(aSignature,[joIgnoreEmptyArrays,joIgnoreEmptyStrings]);
if not assigned(FSignatures) then
FSignatures := TJSONArray.Create;
FSignatures.Add(myJSONValue);
This is the JSON I am sending:
[
{
"signatureData": "\/9j\/4AAQSkZJRgABAQAAAQABAAD\/.."
}
]
Is there a way to get the string in the JSON object without the \?
I tried to add the SignatureData as a pair, but then the value has also \/ in it.
Related
I have a server set up to send messages over a local host port. I am trying to decode the serialized json messages sent by the server and get this error.
Error decoding message: kotlinx.serialization.json.internal.JsonDecodingException: Unexpected JSON token at offset 55: Expected EOF after parsing, but had instead at path: $
JSON input: .....mber":13,"Timestamp":5769784} .....
The Racer State messages are formatted in JSON as follows: { “SensorId”: “value”, “RacerBibNumber” : “value”, “Timestamp” : “value” }, where the value’s are character string representations of the field values. I have also tried changing my RacerStatus Class to take String instead of Int but to a similar error. Am I missing something here? The symbol that is missing in the error was not able to be copied over so I know it's not UTF-8.
I have also added
val inputString = bytes.toString(Charsets.UTF_8)
println("Received input: $inputString")
This gets
Received input: {"SensorId":0,"RacerBibNumber":5254,"Timestamp":3000203}
with a bunch of extraneous symbols at the end.
data class RacerStatus(
var SensorId: Int,
var RacerBibNumber: Int,
var Timestamp: Int
) {
fun encode(): ByteArray {
return Json.encodeToString(serializer(), this).toByteArray()
}
companion object {
fun decode(bytes: ByteArray): RacerStatus {
print(bytes[0])
try {
val mstream = ByteArrayInputStream(bytes)
return Json.decodeFromStream<RacerStatus>(mstream)
} catch (e: SerializationException) {
println("Error decoding message: $e")
return RacerStatus(0, 0, 0)
}
// return Json.decodeFromString(serializer(), mstream.readBytes().toString())
}
}
}
So I found an answer to my question. I added a regex to include just the json components I know my json contains.
val str = bytes.toString(Charsets.UTF_8)
val re = Regex("[^A-Za-z0-9{}:,\"\"]")
return Json.decodeFromString<RacerStatus>(re.replace(str,""))
I thought that Charsets.UTF_8 would remove the misc characters but it did not. Is there a more intiuative solution? Also is there a regex that would cover all possible values in json?
I have in Delphi XE4, TSuperObject:
TAspTransactionBasicData = Class(TObject)
Currency : Byte;
Amount : Currency;
constructor Create(aCurrency: Byte; aAmount: Currency);
end;
TStartWorkflowWithBasicData = Class(TObject)
AdditionalData : TAspTransactionBasicData; // here it is as an Object
TypeOfWorkflow : Byte;
constructor Create(aAdditionalData: TAspTransactionBasicData; aTypeOfWorkflow: Byte);
function toJSon(TObject:TStartWorkflowWithBasicData):String;
end;
and the ToJSon function puts the object into JSON:
function TStartWorkflowWithBasicData.toJSon(TObject:TStartWorkflowWithBasicData):String;
Var
JSon: ISuperObject;
RttiCont: TSuperRttiContext;
begin
Result := '';
RttiCont := TSuperRttiContext.Create;
JSon := RttiCont.AsJson<TStartWorkflowWithBasicData>(TObject); // Insert the object into JSON
Result := JSon.AsJSon(False);
RttiCont.Free;
end;
and I would also need the exact opposite, a function fromJSon, which will read the JSON (where the object was inserted) back into the object, but I'm groping...
Can you please advise me?
I can't help you with SuperObject, but kbmMW contains a very complete XML, JSON, YAML, BSON, MessagePack + CSV and in next release also TXT (fixed format) serializer/deserializer and object marshaller/unmarshaller.
It will easily convert both ways, and even between formats.
kbmMW Community Edition contains all (except the new TXT format), and is free, even for commercial use (limited by license).
https://components4developers.blog/2019/03/11/rest-easy-with-kbmmw-24-xml_json_yaml_to_object_conversion/
My API needs to return the following data in it's response.
{ users: 'All users are as follows: [{id: 1}, {id: 2}]'}
It should be a json object with one of the key values is a json array. However, the json array is turned into a string because it needs to be appended onto another string. My code is like this:
const array = [{id: 1}, {id:2}]
const string = 'All users are as follows: ' + JSON.stringify(array)
res.send({users: string})
I use Express for my API. When I check the response in postman it add many backslashed onto the string. However, when I do console.log({a: string}) locally, I don't see any of those slashes.
this is what I see:
{users: "[{\"id\":1}, {\"id\":2}]"}
{users: "[{\"id\":1}, {\"id\":2}]"}
is the json representation of response , in json string is represented by enclosing it with double quotes (") and so if the string itself contains double quotes then it should be escaped.
{ "user": " "name" " } , is invalid you should use { "user" : "\"name\""}
when you print it in console it prints only the escaped charater thats why you don't see " but ".
learn more about javascript grammer at :
https://www.crockford.com/mckeeman.html
when you use JSON.stringify() it converts it into valid JSON string , you cannot send it without it because it will send it as javascript object and not as valid json. using
res.send ({name:"test"}} will send response as [object][object]
so the only way to get what you want is to send the response as text and not JSON:
const array = [{id: 1}, {id:2}]
const string = 'All users are as follows: ' + JSON.stringify(array)
res.send(`{users: "${string}" }`)
here in res.send isntead of {users:string} , we are using "users:string" .
NOTE: its not valid JSON
Output:
Could you please post your code on returning your response.
Anyways, I do it this way.
let object = {name: "Juan Dela Cruz"}
res.send(object)
I'm trying to write a function that will insert informations in my database using JSON or multiple parameters in the URL.
I already managed to create a function that returns informations from my database to the client but not the other way. Every example I find explains how to creat a JSON but not how to receive it with System.JSON (Delphi 10.2)
Here is a code sample for a GET function actually working on my Datasnap :
function TDM_Test.DS_getArticles(pStock : String): string;
begin
try
VGOutils.PR_logs('Get all articles from table');
VGOutils.FU_CheckConnect('1234567890');
with VGOutils.SQ_temp1 do
begin
SQL.Clear;
SQL.Add('SELECT code, name, price, seller, departement FROM articles');
SQL.Add('WHERE stock');
ParamByName('stock').AsString := pStock;
VGOutils.SQ_temp1.Open;
end;
GetInvocationMetadata().ResponseCode := 200;
GetInvocationMetadata().ResponseContent :=
VGOutils.PR_JSON(VGOutils.SQ_temp1, ['code', 'name', 'price', 'seller']);
except on E: Exception do
PR_error(E.Message);
end;
VGOutils.PR_Disconnect;
end;
Now I need the client to send me new articles to INSERT in my database.
The only thing that I cant figure out is how to declare the function and it's parameters.
I want the client to be able to send me a JSON with this correct format
{"article":[{"code":"AAA","name":"car","price" : "10400.90", "sellers" : [{"seller1" : "Automaniac", "seller2" : "Autopro" }]}]}
Now I know how to parse it with TJSONObject.ParseJSONValue() by reading this JSON RadStudio
EDIT
If this JSON string is hardcoded it works fine with ParseJSONValue but if the string is taken from the URL my JSONstring only contains "]}" and obviously there is nothing to parse.
function TDM_Test.DS_insertArticles(pUrlJsonString: String): string;
// Hardcoded JSON string
jsonString := '{"article":[{"code":"AAA","name":"car","price" : "10400.90", "sellers" : [{"seller1" : "Automaniac", "seller2" : "Autopro" }]}]}';
JSonValue := TJSONObject.ParseJSONValue(jsonString);
// String received in url
jsonString := pUrlJsonString;
JSonValue := TJSONObject.ParseJSONValue(pUrlJsonString);
I found the way I wanted it to work by not using the string parameter of the function but instead using the Custom body by passing a JSONObject.
The method is POST and the content type is application/JSON.
function TDM_Test.DS_insertArticles(pUrlJsonObj: TJSONObject): string;
JSonValue := TJSONObject.ParseJSONValue(pUrlJsonObj);
// Retrieve data for database fields
artCode := JSONValue.GetValue<string>('article[0].code');
artName := JSONValue.GetValue<string>('article[0].name');
artPrice := JSONValue.GetValue<string>('article[0].price');
//... Proceed to INSERT SQL with these values
I am trying to receive a JSON string in salesforce by converting a blob in the body of an Http request. However, when I convert the blob to a string there are \ characters that get inserted into the request which prevents me from parsing.
I then tried to take the string and remove all \ characters... that didn't work either.
RestRequest req = RestContext.request;
Blob jsonBlob = req.requestBody;
String jsonString = jsonBlob.toString();
return jsonString;
The original string (the one that is received as a blob) looks like this:
{"putTimeCard":{"timecard":{"timeCardID": "","employeeID": ""}}
And after converting to a salesforce string and assigned to the jsonString is altered to:
{\"putTimeCard\":{\"timecard\":{\"timeCardID\": \"\",\"employeeID\": \"\"}}
Has anyone found a solution for this?
Thanks
The JSON Deserializer can parse the string with the escape characters. You can either deserialize into an object like so:
String jsonString = '{\"putTimeCard\":{\"timecard\":{\"timeCardID\": \"\",\"employeeID\": \"\"}}}'
Timecard t = (Timecard) JSON.deserialize(jsonString, Type.forName('Timecard'));
or if you just want a map of objects you can do the following:
String jsonString = '{\"putTimeCard\":{\"timecard\":{\"timeCardID\": \"\",\"employeeID\": \"\"}}}'
Map<String, Object> m = (Map<String, Object>) JSON.deserializeUntyped(jsonString);