Send Data packet to Client - ios

I need to sent NSData which holds JSON Strings as well total number of length in form of (length of actual string+actual string).I need to send a packet of data that reserves first 10 bytes for length of string and followed by string
while sending NSData object I also need to send its length in first 10 bytes followed by data like :
length of data + JSON string = total data sent to java client .
further java client will read first 10 byte to know actual length of data coming to make an byte array and move further.

This brute force example uses first 10 characters for string representation of payload length followed by actual payload.
NSArray *arrPayload = #[#"Hello", #"world"];
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:arrPayload
options:0
error:nil];
NSString *jsonString = [[NSString alloc] initWithData:jsonData
encoding:NSUTF8StringEncoding];
NSString *comboString = [NSString stringWithFormat:#"%010lu%#",
(unsigned long)jsonString.length, jsonString];
NSLog(#"%#", comboString);
NSData* combinedData = [comboString dataUsingEncoding:NSUTF8StringEncoding];
result:
0000000017["Hello","world"]
But: if this is supposed to be sent as a HTTP request you might want to consider using Content-Length header to pass the length information instead.

Related

Change UIImage Class to send to node.js server in iOS?

I am creating an App for chatting. Now I want to send UIImage to server in JSON String so other user can receive image.I am using socket.io so I have to send event with data(JSON String).
Problems- When I try to convert UIImage to NSData and convert it to JSON it gives error 'Invalid type in JSON write (NSConcreteMutableData)'.
What will be the correct way to send UIImage to server?
code
NSData *imgData = UIImageJPEGRepresentation(image, .2);
NSString * imageString =[[NSString alloc]initWithBytes:[imageData bytes] length:[imageData length] encoding:NSASCIIStringEncoding];
also tried
NSString * imageString =[[NSString alloc]initWithData :imgData encoding:NSUTF8StringEncoding];
converted data to dictionary:
NSDictionary *jsonDict = [NSJSONSerialization JSONObjectWithData:imgData options:NSJSONReadingAllowFragments error:&error];
Any help would be appreciated.
The general approach would be to base64 encode the image data. In this way the image data is converted to a string format instead of binary.
Since iOS 7 NSData has provided base64 conversion methods that you can use instead of your current attempted conversion to and from strings.

A string encoding issuse on IOS

I came across a problem with string encoding in ios development. The story is as below:
I create some values in Chinese and then create a NSDictionary for those values, the dictionary is used as parameter for network request:
- (void)createActivity
{
NSString *actionTheme = titleF.text;
NSString *actionTitle = biaotiF.text;
NSDictionary *dic = [NSDictionary dictionaryWithObjectsAndKeys:actionTheme, #"actionTheme", actionTitle, #"actionTitle",nil];
[self networkrequest:];
}
Then some work has been done for the dictionary:
Transform the dictionary to the form of JSON as the type of NSString.
NSData* jsonData = [NSJSONSerialization dataWithJSONObject:param options:NSJSONWritingPrettyPrinted error:nil];
NSString *jsonString = [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding];
Encoding the string , because of Chinese word in the string.
NSString *urlEncodedString = [jsonString stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding];
At last a full url was create with the string above:
http://app.ic100.com/action/add?paramJson=%7B%22actionTheme%22%3A%22%E6%88%96%E8%80%85%E5%92%8C%E7%94%9F%E6%B4%BB%22%2C%22actionSite%22%3A%22%E5%8E%A (something like this)
I use the third party "ASIFormDataRequest" for network request, and I also set the StringEncoding:
ASIFormDataRequest *requstHttp = [[ASIFormDataRequest alloc] init];
[requstHttp setStringEncoding:NSUTF8StringEncoding];
....
All the datas has been sent to the server successfully, but when I request these data from the server and show then on the iphone. It turn to be unreadable text:
I have carefully checked all the place that I should encode or decode the string, and only utf8 is used. What`s more , for the server side , no other encoding used either. And my colleague has tested sent data from Android platform, no problem. So I think maybe I have missed some points.
Any advise?
By using the class Base64 you can encode or decode the string.
Add Base64 class in your project from HERE
see the mehode in class to encode.
Encode:
+ (NSString *)stringWithBase64EncodedString:(NSString *)string;
- (NSString *)base64EncodedString;
Decode:
- (NSString *)base64DecodedString;

Break image/jpeg into chunks and bind in nsdictionary for sending JSON in iOS

EDIT: I did not do a very good job of explaining for the server works and my apologies for the same. So here are two things in which the server works ( expects data from clients)
1) Server has a size limitation for receiving image data. It expects images to be broken up in chunks of byte array
2) Server expects to receive these chunks of byte array through JSON.
So I am assuming this translates to the following on the client side
1) I need to break the image in parts
2) Create a Byte array of each part
3) Bind those byte array with JSON and send with server
Once received by the server, those are constructed as an Image by the server.
I am trying to achieve the above mentioned goal by the following approach (I keep the image file in NSData, then I create a Byte Buffer and keep chunks of the image file's NSData in that buffer. Post that I bind this buffer with JSON )
Following is the code for above approach:
-(void)dividepacketId:(int)pktId fileData:(NSData*)dt //dt contain the NSData of image file
{
Byte buffer[20480];
long long dtLength,from=0;
long long len=[dt length];
BOOL b=YES;
while (b)
{
int k=0,indexCont=0;
if(len>20480)
{
dtLength=20480;
}
else
{
dtLength=len;
b=NO;
}
[dt getBytes:buffer range:NSMakeRange(from,dtLength)];
NSData *imageData=nil;
imageData = [NSData dataWithBytes:buffer length:dtLength];
len=len-dtLength;
from=from+dtLength;
NSLog(#"sending buffer=%s legth of buffer=%lli len value=%lli",buffer,dtLength,len); //everything is fine till here
NSMutableDictionary *projectDictionary3 = [NSMutableDictionary dictionaryWithCapacity:1];
[projectDictionary3 setObject:#"2100" forKey:#"Action"];
[projectDictionary3 setObject:[NSString stringWithFormat:#"%i",pktId] forKey:#"PacketId"];
[projectDictionary3 setObject:#"101" forKey:#"FileAction"];
if(imageData!=nil)
[projectDictionary3 setObject: imageData forKey:#"FData"];//data
[projectDictionary3 setObject:[NSString stringWithFormat:#"%i",(int)dtLength] forKey:#"DataLength"];//data
NSError *jsonSerializationError = nil;
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:projectDictionary3 options:NSJSONWritingPrettyPrinted error:&jsonSerializationError]; //"here crashed"
if(!jsonSerializationError)
{
NSString *serJSON = [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding];
NSLog(#"Serialized JSON: %#", serJSON);
}
else
{
NSLog(#"JSON Encoding Failed: %#", [jsonSerializationError localizedDescription]);
}
code to send over stream
[self sendDataToServer:jsonData];
} //while loop
}
Here is the challenge. If I send simple data (for example a string) through this code, it goes over to server successfully ( through socket). But when I try to break an actual jpeg image into parts and bind it in nsdictionary to make json, it crashes with the following error.
terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'Invalid type in JSON write (NSConcreteData)'. Any help here would be highly appreciated.
EDIT: As explained by bobnoble, I understand the reason for the exception. In that case however, how do I accomplish sending over data to server
Deleting all but the key portions that need to be changed.
As I stated in the comments the data needs to be in a format JSON handles, raw bytes are not acceptable so one way is to encode the data with Base64. The receiver will also need to decode the Base64 string into data.
while (b) {
//get chunk from and dtLength
NSData *imageData = [dt subdataWithRange:NSMakeRange(from, dtLength)];
NSData *imageBase64Data = [imageData base64EncodedDataWithOptions:0];
NSString *imageBase64String = [[NSString alloc] initWithData:imageBase64Data encoding: NSUTF8StringEncoding];
// update len and from
NSLog(#"sending imageData =%#. dtLength =%i len =%lli", imageBase64String, dtLength, len);
// Create projectDictionary3 and add items
// Added image data)
if(imageData.length) {
[projectDictionary3 setObject: imageBase64String forKey:#"FData"];
}
[projectDictionary3 setObject:#(imageBase64String.length) forKey:#"DataLength"];
// serialize projectDictionary3 into JSON and sent to server];
}
From the NSJSONSerialization class reference:
An object that may be converted to JSON must have the following
properties:
The top level object is an NSArray or NSDictionary.
All objects are instances of NSString, NSNumber, NSArray, NSDictionary, or NSNull.
All dictionary keys are instances of NSString.
Numbers are not NaN or infinity.
The second bullet does not include NSData, and is why the exception is being thrown.
Convert the image data to Base64 encoding, then put it in the dictionary as an NSString. Take a look at the NSData base64EncodedStringWithOptions method.

how to send an array as a parameter to json service in iOS

I am using iPhone JSON Web Service based app.I need to pass input parameter as an array to a JSON web Service, how can I do this?
Array Contains 12 elements.
Here am providing sample service...
input parametes for this service:
dev_id = 1;
dev_name= josh and array items (projectslist,companyidentifier)
http://www.jyoshna.com/api/developer.php?dev_id=1&dev_name=josh&(Here i need to pass the array elements)
can any help us how to pass array as a input parameter to the json service?
First you have to convert array as JSON string
NSString *requestString=[jsonParser stringWithObject:array];
convert string to data
NSData *data=[requestString dataUsingEncoding:NSUTF8StringEncoding];
set that data as request Body
[request setHTTPBody:data];
You have to serialize the array and pass as an argument. Dont forget to unserialize in server side
you will need to create an NSMutabelDictionary of your array then JSON encode it, you can then send the resulting string you your webservice however you choose. I tend to build a POST request and send it that way
NSMutableDictionary *jsonDict = [[NSMutableDictionary alloc] init];
NSMutableDictionary *tagData = [[NSMutableDictionary alloc] init];
for(int i = 0; i < array.count; i++)
{
NSString *keyString = [NSString stringWithFormat:#"key%i", i];
[tagData setObject:[array objectAtIndex:i] forKey:keyString];
}
[jsonDict setObject:tagData forKey:#"entries"];
NSData* data = [NSJSONSerialization dataWithJSONObject:jsonDict
options:NSJSONWritingPrettyPrinted error:&error];
NSString* aStr;
aStr = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
It is the sgtring aStr that you need to send

iOS : decode utf8 string

I'm receiving a json data from server with some strings inside. I use SBJson https://github.com/stig/json-framework to get them.
However when I output some strings at UILabel they look like this: \u0418\u043b\u044c\u044f\u0411\u043b\u043e\u0445 (that's Cyrillic symbols)
And it's all right with latin characters
How can I decode it into normal symbols?
Some code about getting data:
NSData * data = [NSURLConnection sendSynchronousRequest:request returningResponse:&response error:&error];
NSString *stringData = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
NSDictionary *object = [parser objectWithString:stringData error:nil];
NSString *comments = [NSString stringWithFormat:#"%#",[object valueForKey:#"comments"]];
String comments has a very special format, so I'm doing some operation like stringByTrimmingCharactersInSet ,
stringByReplacingOccurrencesOfString ,
NSArray* json_fields = [comments_modified componentsSeparatedByString: #";"];
to get a final data.
This is an example of received data after some trimming/replacing (it's NSString* comments):
"already_wow"=0;"date_created"="2012/03/1411:11:18";id=41598;name="\U0418\U043b\U044c\U044f\U0411\U043b\U043e\U0445";text="\U0438\U043d\U0442\U0435\U0440\U0435\U0441\U043d\U043e";"user_id"=1107;"user_image"="user_image/a6/6f/96/21/20111220234109510840_1107.jpg";"user_is_deleted"=0;username=IlyaBlokh;"wow_count"=0;
You see that fields text and name are encoded
If I display them on the view (at UILabel for example), they still look the same
maybe the string returned is just the unicode string representation (ascii string), that's means not returned the content encoded with utf8, to try this with NSASCIIStringEncoding to get stringData

Resources