forked from alexkolson/kynetx-objc
-
Notifications
You must be signed in to change notification settings - Fork 0
/
kynetx.m
162 lines (132 loc) · 5.7 KB
/
kynetx.m
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
//
// kynetx.m
// kynetx-desktop
//
// Created by Alex on 12/23/10.
// Copyright 2010 Kynetx. All rights reserved.
//
#import "Kynetx.h"
@implementation Kynetx
// property synthesis
@synthesize appID;
@synthesize eventDomain;
- (id) init {
// just pass nil to designated initializer
return [self initWithAppID:nil eventDomain:nil];
}
// this is the designated initializer
- (id) initWithAppID:(id) input eventDomain:(id) domain {
if (self = [super init]) {
[self setAppID:input];
[self setEventDomain:domain];
}
return self;
}
- (void) signal:(NSString *) name params:(NSDictionary*) params {
// raise events to kns
// build the request URL
// start with a NSString base URL
NSString* baseURLstring = [NSString stringWithFormat:@"https://cs.kobj.net/blue/event/%@/%@/%@/", [self eventDomain], name, [self appID]];
// then construct NSURL with the dict of params and baseURLstring
NSURL* eventURL = [self URLFromDict:params withBaseURL:baseURLstring];
// construct a request object with eventURL
NSMutableURLRequest* KNSRequest = [[[NSURLRequest alloc] initWithURL:eventURL] autorelease];
// grab KNS cookies
NSArray* KNSCookies = [[NSHTTPCookieStorage sharedHTTPCookieStorage] cookiesForURL:eventURL];
// get a dictionary of HTTP headers using the cookies
NSDictionary* headers = [NSHTTPCookie requestHeaderFieldsWithCookies:KNSCookies];
// set request headers from the dictionary of headers
[KNSRequest setAllHTTPHeaderFields:headers];
// then use that request to make a connection
// specifying that the current object should act as its delegate
[[NSURLConnection alloc] initWithRequest:KNSRequest delegate:self];
}
- (void) connection:(NSURLConnection *)connection didReceiveResponse:(NSURLResponse *)response {
// handle cookies
// cast base response to derived http url response class
// so we can access headers
NSHTTPURLResponse* KNSHTTPResponse = (NSHTTPURLResponse*) response;
// retrieve the cookies from the KNS response Set-Cookie header
// KNS just sends one Set-Cookie header, but this method will handle any
// number of returned Set-Cookie headers
NSArray* KNSCookies = [NSHTTPCookie cookiesWithResponseHeaderFields:[KNSHTTPResponse allHeaderFields]
forURL:[KNSHTTPResponse URL]];
// add the KNSCookies to the shared cookie storage of the device
[[NSHTTPCookieStorage sharedHTTPCookieStorage] setCookies:KNSCookies
forURL:[KNSHTTPResponse URL] mainDocumentURL:nil];
}
- (void) connection:(NSURLConnection *)connection didReceiveData:(NSData *)data {
// take returned data and parse it
// Then call KynetxDelegate method, passing it the
// dictionary of directives
// This is where we exit the current Kynetx
// object if everything goes well
NSArray* KNSDirectives = [self parseDirectives:data];
}
- (NSArray*) parseDirectives:(NSData*) response {
// parse json string of directives returned from KNS
// create an instance of the json parser
SBJsonParser* parser = [[[SBJsonParser alloc] init] autorelease];
// get a string representation of the NSData response
// make sure it is UTF-8 encoded
NSString* responseString = [[[NSString alloc] initWithData:response encoding:NSUTF8StringEncoding] autorelease];
// make a range that will be used to strip
// the comment from the KNS response
NSRange knsCommentRange = NSMakeRange(0, 32);
// strip the comment off using the range
NSString* jsonString = [responseString stringByReplacingCharactersInRange:knsCommentRange withString:@""];
// pass json parser the jsonString, and grab the directives object on the now-parsed json
NSArray* rawDirectives = [[parser objectWithString:jsonString] objectForKey:@"directives"];
// setup array to hold reworked directives
NSMutableArray* directives = [[[NSMutableArray alloc] initWithCapacity:20] autorelease];
// rework each directive in the rawDirectives
// array and add it to the directives array
for (NSDictionary *rawDirective in rawDirectives) {
NSDictionary* meta = [rawDirective objectForKey:@"meta"];
NSDictionary* directive = [NSDictionary dictionaryWithObjectsAndKeys:
[meta objectForKey:@"rid"], @"rid",
[meta objectForKey:@"rule_name"], @"rule_name",
[meta objectForKey:@"txn_id"], @"txn_id",
[rawDirective objectForKey:@"name"], @"action",
[rawDirective objectForKey:@"options"], @"options",
nil];
[directives addObject:directive];
}
return directives;
}
- (NSURL*) URLFromDict:(NSDictionary*) params withBaseURL:(NSString*) URLstring {
// construct a NSURL from a dictionary of paramaters and a base URL string
// setup mutable string
NSMutableString* buildString = [[[NSMutableString alloc] init] autorelease];
// make a range to check for a question mark in URLString
NSRange questionMarkRange = [URLstring rangeOfString:@"?"];
if (questionMarkRange.location == NSNotFound || questionMarkRange.location != URLstring.length - 1) {
// if the base url string does not have a question mark at the end, we need to add it
[buildString appendFormat:@"%@%@", URLstring, @"?"];
} else {
// no question mark needed
[buildString appendString:URLstring];
}
// loop over the params dictionary
// appending each key-value pair as we go
NSArray* keys = [params allKeys];
int count = [keys count];
for (int i = 0; i < count; i++) {
id key = [keys objectAtIndex:i];
id value = [params objectForKey:key];
if (i != count - 1) {
[buildString appendFormat:@"%@=%@&",key,value];
} else {
[buildString appendFormat:@"%@=%@",key,value];
}
}
// at this point, URL is now constructed and ready to be returned
return [[[NSURL alloc] initWithString:buildString] autorelease];
}
// destructor
- (void) dealloc {
[appID release];
[eventDomain release];
[super dealloc];
}
@end