Skip to content

Commit 4237782

Browse files
authored
Fix leak (#326)
* Refactored Networking Requests * Instead of having to manually build an HTTP request every time the app needs to make a request with the backend, this commit simplifies the process by encapsulating all of this code in a few classes. * Also fixes an issue with registerUser where location data was not being sent. The location data was being added to 'dataDic' after it got serialized into JSON data * Fixed broken test * Forgot to import appropriate headers breaking a test. * Added NSURLSession attachment download code * Closed the url_session branch since it is now obsolete * Removed old header method declarations * Due to the fact that we've switched to a new rest model, the old enqueueRequest:onSuccess... method is no longer needed and has been removed from the project * Also removed the overrider for this method from unit test shadows * PR Fixes, Adds correct copyright to header, fixes typos * Fixes some typos * Accesses OneSignalClient sharedClient using a property accessor instead of a method getter for cleaner syntax * Moves JSON parser method to OneSignalClient class for logical consistency * Removes unnecessary log statements * Fixes Buttons for Push Notifications in iOS 7 * Fixes an issue iOS 7, buttons were not being shown on the UIAlertView when the app was in focus. * Also fixes an issue where the button action ID wasn't being forwarded to the host application (via OSHandleNotificationActionBlock) * Remove HTTP Client * Minor commit to remove the OneSignalHTTPClient from the project since it is no longer used. * Fixes a memory leak * Resolves a memory leak introduced by creating NSURLSession instances and not calling [session finishTasksAndInvalidate]. The effect of this leak was relatively small since it only leaks 600 bytes per request, but it does add up over time. * Shared NSURLSession Instance * Switched OneSignalClient to use a single shared instance of NSURLSession instead of creating a new instance for every HTTP request. * For the Extension image download function, added a function call in OneSignalHelper.m so that the NSURLSession instance is not leaked. * App ID Requirement Fix • Fixed an issue in this branch where the Get iOS Params request was displaying a 'missing App ID' error in the debug console. • Added logging for verbose mode showing HTTP requests & parameters • Made it so that requests that require an app ID yet are given a nil/empty app ID will return an NSError and log an error to the console. * Fix Small Memory Leak • Fixed a small memory leak in OneSignalLocation • malloc() was being used to initialize a temporary location but free() was never called on it so it never got released • Also, added a required CLLocationManager delegate method to prevent a crash in the event of a location manager error
1 parent 3ff4462 commit 4237782

File tree

13 files changed

+70
-150
lines changed

13 files changed

+70
-150
lines changed

iOS_SDK/OneSignalSDK/OneSignal.xcodeproj/project.pbxproj

Lines changed: 0 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -47,10 +47,6 @@
4747
912412131E73342200E41FD7 /* OneSignalAlertViewDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = 912411F31E73342200E41FD7 /* OneSignalAlertViewDelegate.m */; };
4848
912412141E73342200E41FD7 /* OneSignalAlertViewDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = 912411F31E73342200E41FD7 /* OneSignalAlertViewDelegate.m */; };
4949
912412151E73342200E41FD7 /* OneSignalHelper.h in Headers */ = {isa = PBXBuildFile; fileRef = 912411F41E73342200E41FD7 /* OneSignalHelper.h */; };
50-
912412191E73342200E41FD7 /* OneSignalHTTPClient.h in Headers */ = {isa = PBXBuildFile; fileRef = 912411F61E73342200E41FD7 /* OneSignalHTTPClient.h */; };
51-
9124121A1E73342200E41FD7 /* OneSignalHTTPClient.m in Sources */ = {isa = PBXBuildFile; fileRef = 912411F71E73342200E41FD7 /* OneSignalHTTPClient.m */; };
52-
9124121B1E73342200E41FD7 /* OneSignalHTTPClient.m in Sources */ = {isa = PBXBuildFile; fileRef = 912411F71E73342200E41FD7 /* OneSignalHTTPClient.m */; };
53-
9124121C1E73342200E41FD7 /* OneSignalHTTPClient.m in Sources */ = {isa = PBXBuildFile; fileRef = 912411F71E73342200E41FD7 /* OneSignalHTTPClient.m */; };
5450
9124121D1E73342200E41FD7 /* OneSignalJailbreakDetection.h in Headers */ = {isa = PBXBuildFile; fileRef = 912411F81E73342200E41FD7 /* OneSignalJailbreakDetection.h */; };
5551
9124121E1E73342200E41FD7 /* OneSignalJailbreakDetection.m in Sources */ = {isa = PBXBuildFile; fileRef = 912411F91E73342200E41FD7 /* OneSignalJailbreakDetection.m */; };
5652
9124121F1E73342200E41FD7 /* OneSignalJailbreakDetection.m in Sources */ = {isa = PBXBuildFile; fileRef = 912411F91E73342200E41FD7 /* OneSignalJailbreakDetection.m */; };
@@ -214,8 +210,6 @@
214210
912411F31E73342200E41FD7 /* OneSignalAlertViewDelegate.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = OneSignalAlertViewDelegate.m; sourceTree = "<group>"; };
215211
912411F41E73342200E41FD7 /* OneSignalHelper.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = OneSignalHelper.h; sourceTree = "<group>"; };
216212
912411F51E73342200E41FD7 /* OneSignalHelper.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = OneSignalHelper.m; sourceTree = "<group>"; };
217-
912411F61E73342200E41FD7 /* OneSignalHTTPClient.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = OneSignalHTTPClient.h; sourceTree = "<group>"; };
218-
912411F71E73342200E41FD7 /* OneSignalHTTPClient.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = OneSignalHTTPClient.m; sourceTree = "<group>"; };
219213
912411F81E73342200E41FD7 /* OneSignalJailbreakDetection.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = OneSignalJailbreakDetection.h; sourceTree = "<group>"; };
220214
912411F91E73342200E41FD7 /* OneSignalJailbreakDetection.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = OneSignalJailbreakDetection.m; sourceTree = "<group>"; };
221215
912411FA1E73342200E41FD7 /* OneSignalLocation.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = OneSignalLocation.h; sourceTree = "<group>"; };
@@ -407,8 +401,6 @@
407401
912411F11E73342200E41FD7 /* OneSignal.m */,
408402
912411F41E73342200E41FD7 /* OneSignalHelper.h */,
409403
912411F51E73342200E41FD7 /* OneSignalHelper.m */,
410-
912411F61E73342200E41FD7 /* OneSignalHTTPClient.h */,
411-
912411F71E73342200E41FD7 /* OneSignalHTTPClient.m */,
412404
912411F81E73342200E41FD7 /* OneSignalJailbreakDetection.h */,
413405
912411F91E73342200E41FD7 /* OneSignalJailbreakDetection.m */,
414406
912411FA1E73342200E41FD7 /* OneSignalLocation.h */,
@@ -522,7 +514,6 @@
522514
9124123D1E73342200E41FD7 /* UIApplicationDelegate+OneSignal.h in Headers */,
523515
9124121D1E73342200E41FD7 /* OneSignalJailbreakDetection.h in Headers */,
524516
9129C6B71E89E59B009CB6A0 /* OSPermission.h in Headers */,
525-
912412191E73342200E41FD7 /* OneSignalHTTPClient.h in Headers */,
526517
912412151E73342200E41FD7 /* OneSignalHelper.h in Headers */,
527518
91F58D7F1E7C7F5F0017D24D /* OneSignalNotificationSettingsIOS10.h in Headers */,
528519
912412391E73342200E41FD7 /* OneSignalWebView.h in Headers */,
@@ -684,7 +675,6 @@
684675
912412261E73342200E41FD7 /* OneSignalMobileProvision.m in Sources */,
685676
454F94F21FAD218000D74CCF /* OneSignalNotificationServiceExtensionHandler.m in Sources */,
686677
912412321E73342200E41FD7 /* OneSignalTracker.m in Sources */,
687-
9124121A1E73342200E41FD7 /* OneSignalHTTPClient.m in Sources */,
688678
91B6EA411E85D38F00B5CF01 /* OSObservable.m in Sources */,
689679
4529DF0C1FA932AC00CEAB1D /* OneSignalTrackFirebaseAnalytics.m in Sources */,
690680
91F58D891E7C9A240017D24D /* OneSignalNotificationSettingsIOS7.m in Sources */,
@@ -720,7 +710,6 @@
720710
0338566C1FBBDB150002F7C1 /* OneSignalNotificationServiceExtensionHandler.m in Sources */,
721711
912412271E73342200E41FD7 /* OneSignalMobileProvision.m in Sources */,
722712
912412331E73342200E41FD7 /* OneSignalTracker.m in Sources */,
723-
9124121B1E73342200E41FD7 /* OneSignalHTTPClient.m in Sources */,
724713
91B6EA421E85D38F00B5CF01 /* OSObservable.m in Sources */,
725714
91F58D8A1E7C9A240017D24D /* OneSignalNotificationSettingsIOS7.m in Sources */,
726715
912412231E73342200E41FD7 /* OneSignalLocation.m in Sources */,
@@ -757,7 +746,6 @@
757746
4529DED51FA823B900CEAB1D /* TestHelperFunctions.m in Sources */,
758747
911E2CBD1E398AB3003112A4 /* UnitTests.m in Sources */,
759748
91B6EA431E85D38F00B5CF01 /* OSObservable.m in Sources */,
760-
9124121C1E73342200E41FD7 /* OneSignalHTTPClient.m in Sources */,
761749
4529DEDE1FA828E500CEAB1D /* NSDateOverrider.m in Sources */,
762750
CA08FC871FE99BB4004C445F /* OneSignalClientOverrider.m in Sources */,
763751
912412401E73342200E41FD7 /* UIApplicationDelegate+OneSignal.m in Sources */,

iOS_SDK/OneSignalSDK/Source/OSNotificationPayload.m

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -96,6 +96,8 @@ -(void)parseOSDataPayload {
9696
[self parseActionButtons:os_data[@"buttons"]];
9797
} else if (os_data[@"buttons"] && [os_data[@"buttons"] isKindOfClass: [NSDictionary class]] && [os_data[@"buttons"][@"o"] isKindOfClass: [NSArray class]]) {
9898
[self parseActionButtons:os_data[@"buttons"][@"o"]];
99+
} else if ([_rawPayload[@"actionbuttons"] isKindOfClass:[NSArray class]]) {
100+
[self parseActionButtons:_rawPayload[@"actionbuttons"]];
99101
}
100102
}
101103

iOS_SDK/OneSignalSDK/Source/OneSignal.m

Lines changed: 0 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,6 @@
2828
#import "OneSignal.h"
2929
#import "OneSignalInternal.h"
3030
#import "OneSignalTracker.h"
31-
#import "OneSignalHTTPClient.h"
3231
#import "OneSignalTrackIAP.h"
3332
#import "OneSignalLocation.h"
3433
#import "OneSignalReachability.h"
@@ -154,15 +153,6 @@ @implementation OneSignal
154153
BOOL disableBadgeClearing = NO;
155154
BOOL mShareLocation = YES;
156155

157-
158-
159-
static OneSignalHTTPClient *_httpClient;
160-
+ (OneSignalHTTPClient*)httpClient {
161-
if (!_httpClient)
162-
_httpClient = [OneSignalHTTPClient new];
163-
return _httpClient;
164-
}
165-
166156
static OSNotificationDisplayType _inFocusDisplayType = OSNotificationDisplayTypeInAppAlert;
167157
+ (void)setInFocusDisplayType:(OSNotificationDisplayType)value {
168158
NSInteger op = value;
@@ -293,7 +283,6 @@ + (void) setWaitingForApnsResponse:(BOOL)value {
293283

294284
+ (void)clearStatics {
295285
app_id = nil;
296-
_httpClient = nil;
297286
_osNotificationSettings = nil;
298287
waitingForApnsResponse = false;
299288
mLastNotificationTypes = -1;

iOS_SDK/OneSignalSDK/Source/OneSignalAlertViewDelegate.m

Lines changed: 12 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -99,24 +99,26 @@ - (void)alertView:(UIAlertView*)alertView clickedButtonAtIndex:(NSInteger)button
9999
actionType = OSNotificationActionTypeActionTaken;
100100

101101
NSMutableDictionary* userInfo = [mMessageDict mutableCopy];
102-
103-
if (mMessageDict[@"os_data"]) {
102+
103+
//fixed for iOS 7, which has 'actionbuttons' as a root property of the dict, not in 'os_data'
104+
if (mMessageDict[@"os_data"] && !mMessageDict[@"actionbuttons"]) {
104105
if ([mMessageDict[@"os_data"][@"buttons"] isKindOfClass:[NSDictionary class]])
105106
userInfo[@"actionSelected"] = mMessageDict[@"os_data"][@"buttons"][@"o"][buttonIndex - 1][@"i"];
106107
else
107108
userInfo[@"actionSelected"] = mMessageDict[@"os_data"][@"buttons"][buttonIndex - 1][@"i"];
108-
}
109-
else if (mMessageDict[@"buttons"])
109+
} else if (mMessageDict[@"buttons"]) {
110110
userInfo[@"actionSelected"] = mMessageDict[@"buttons"][buttonIndex - 1][@"i"];
111-
else {
112-
NSMutableDictionary* customDict = [userInfo[@"custom"] mutableCopy];
113-
NSMutableDictionary* additionalData = [[NSMutableDictionary alloc] initWithDictionary:customDict[@"a"]];
111+
} else {
112+
NSMutableDictionary* customDict = userInfo[@"custom"] ? [userInfo[@"custom"] mutableCopy] : [NSMutableDictionary new];
113+
NSMutableDictionary* additionalData = customDict[@"a"] ? [[NSMutableDictionary alloc] initWithDictionary:customDict[@"a"]] : [NSMutableDictionary new];
114114

115-
if([additionalData[@"actionButtons"] isKindOfClass:[NSArray class]])
115+
if([additionalData[@"actionButtons"] isKindOfClass:[NSArray class]]) {
116116
additionalData[@"actionSelected"] = additionalData[@"actionButtons"][buttonIndex - 1][@"id"];
117-
118-
else if([mMessageDict[@"o"] isKindOfClass:[NSArray class]])
117+
} else if([mMessageDict[@"o"] isKindOfClass:[NSArray class]]) {
119118
additionalData[@"actionSelected"] = mMessageDict[@"o"][buttonIndex -1][@"i"];
119+
} else if ([mMessageDict[@"actionbuttons"] isKindOfClass:[NSArray class]]) {
120+
additionalData[@"actionSelected"] = mMessageDict[@"actionbuttons"][buttonIndex - 1][@"i"];
121+
}
120122

121123
customDict[@"a"] = additionalData;
122124
userInfo[@"custom"] = customDict;

iOS_SDK/OneSignalSDK/Source/OneSignalClient.m

Lines changed: 37 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,10 @@
2828
#import "OneSignalClient.h"
2929
#import "UIApplicationDelegate+OneSignal.h"
3030

31+
@interface OneSignalClient ()
32+
@property (strong, nonatomic) NSURLSession *sharedSession;
33+
@end
34+
3135
@implementation OneSignalClient
3236

3337
+ (OneSignalClient *)sharedClient {
@@ -39,35 +43,39 @@ + (OneSignalClient *)sharedClient {
3943
return sharedClient;
4044
}
4145

46+
-(instancetype)init {
47+
if (self = [super init]) {
48+
_sharedSession = [NSURLSession sessionWithConfiguration:[NSURLSessionConfiguration defaultSessionConfiguration]];
49+
}
50+
51+
return self;
52+
}
53+
4254
- (void)executeRequest:(OneSignalRequest *)request onSuccess:(OSResultSuccessBlock)successBlock onFailure:(OSFailureBlock)failureBlock {
43-
if (!request.hasAppId) {
44-
[OneSignal onesignal_Log:ONE_S_LL_DEBUG message:@"HTTP Requests must contain app_id parameter"];
55+
if (![self validRequest:request]) {
56+
[self handleMissingAppIdError:failureBlock withRequest:request];
4557
return;
4658
}
4759

48-
let sess = [NSURLSession sessionWithConfiguration:[NSURLSessionConfiguration defaultSessionConfiguration]];
49-
50-
let task = [sess dataTaskWithRequest:request.request completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) {
60+
let task = [self.sharedSession dataTaskWithRequest:request.request completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) {
5161
[OneSignalClient handleJSONNSURLResponse:response data:data error:error onSuccess:successBlock onFailure:failureBlock];
5262
}];
5363

5464
[task resume];
5565
}
5666

5767
- (void)executeSynchronousRequest:(OneSignalRequest *)request onSuccess:(OSResultSuccessBlock)successBlock onFailure:(OSFailureBlock)failureBlock {
58-
if (!request.hasAppId) {
59-
[OneSignal onesignal_Log:ONE_S_LL_DEBUG message:@"HTTP Requests must contain app_id parameter"];
68+
if (![self validRequest:request]) {
69+
[self handleMissingAppIdError:failureBlock withRequest:request];
6070
return;
6171
}
6272

63-
let sess = [NSURLSession sessionWithConfiguration:[NSURLSessionConfiguration defaultSessionConfiguration]];
64-
6573
__block NSURLResponse *httpResponse;
6674
__block NSError *httpError;
6775

6876
dispatch_semaphore_t semaphore = dispatch_semaphore_create(0);
6977

70-
let dataTask = [sess dataTaskWithRequest:request.request completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) {
78+
let dataTask = [self.sharedSession dataTaskWithRequest:request.request completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) {
7179
httpResponse = response;
7280
httpError = error;
7381

@@ -81,6 +89,24 @@ - (void)executeSynchronousRequest:(OneSignalRequest *)request onSuccess:(OSResul
8189
[OneSignalClient handleJSONNSURLResponse:httpResponse data:nil error:httpError onSuccess:successBlock onFailure:failureBlock];
8290
}
8391

92+
- (void)handleMissingAppIdError:(OSFailureBlock)failureBlock withRequest:(OneSignalRequest *)request {
93+
let errorDescription = [NSString stringWithFormat:@"HTTP Request (%@) must contain app_id parameter", NSStringFromClass([request class])];
94+
95+
[OneSignal onesignal_Log:ONE_S_LL_ERROR message:errorDescription];
96+
97+
failureBlock([NSError errorWithDomain:@"OneSignalError" code:-1 userInfo:@{@"error" : errorDescription}]);
98+
}
99+
100+
- (BOOL)validRequest:(OneSignalRequest *)request {
101+
if (request.missingAppId) {
102+
return false;
103+
}
104+
105+
[OneSignal onesignal_Log:ONE_S_LL_VERBOSE message:[NSString stringWithFormat:@"HTTP Request (%@) with URL: %@, with parameters: %@", NSStringFromClass([request class]), request.request.URL.absoluteString, request.parameters]];
106+
107+
return true;
108+
}
109+
84110

85111
+ (void)handleJSONNSURLResponse:(NSURLResponse*) response data:(NSData*) data error:(NSError*) error onSuccess:(OSResultSuccessBlock)successBlock onFailure:(OSFailureBlock)failureBlock {
86112

@@ -106,8 +132,7 @@ + (void)handleJSONNSURLResponse:(NSURLResponse*) response data:(NSData*) data er
106132
else
107133
successBlock(nil);
108134
}
109-
}
110-
else if (failureBlock != nil) {
135+
} else if (failureBlock != nil) {
111136
if (innerJson != nil && error == nil)
112137
failureBlock([NSError errorWithDomain:@"OneSignalError" code:statusCode userInfo:@{@"returned" : innerJson}]);
113138
else if (error != nil)

iOS_SDK/OneSignalSDK/Source/OneSignalHTTPClient.h

Lines changed: 0 additions & 34 deletions
This file was deleted.

iOS_SDK/OneSignalSDK/Source/OneSignalHTTPClient.m

Lines changed: 0 additions & 60 deletions
This file was deleted.

iOS_SDK/OneSignalSDK/Source/OneSignalHelper.m

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -117,6 +117,8 @@ + (BOOL)downloadItemAtURL:(NSURL *)url toFile:(NSString *)localPath error:(NSErr
117117

118118
[task resume];
119119

120+
[session finishTasksAndInvalidate];
121+
120122
while (![delegate isDone]) {
121123
[[NSRunLoop currentRunLoop] runUntilDate:[NSDate dateWithTimeIntervalSinceNow:1.0]];
122124
}

iOS_SDK/OneSignalSDK/Source/OneSignalLocation.m

Lines changed: 10 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,6 @@
2828
#import <UIKit/UIKit.h>
2929

3030
#import "OneSignalLocation.h"
31-
#import "OneSignalHTTPClient.h"
3231
#import "OneSignalHelper.h"
3332
#import "OneSignal.h"
3433
#import "OneSignalClient.h"
@@ -219,13 +218,13 @@ - (void)locationManager:(id)manager didUpdateLocations:(NSArray *)locations {
219218
[invocation invoke];
220219
[invocation getReturnValue:&cords];
221220

222-
os_last_location *currentLocation = (os_last_location*)malloc(sizeof(os_last_location));
223-
currentLocation->verticalAccuracy = [[location valueForKey:@"verticalAccuracy"] doubleValue];
224-
currentLocation->horizontalAccuracy = [[location valueForKey:@"horizontalAccuracy"] doubleValue];
225-
currentLocation->cords = cords;
226-
227221
@synchronized(OneSignalLocation.mutexObjectForLastLocation) {
228-
lastLocation = currentLocation;
222+
if (!lastLocation)
223+
lastLocation = (os_last_location*)malloc(sizeof(os_last_location));
224+
225+
lastLocation->verticalAccuracy = [[location valueForKey:@"verticalAccuracy"] doubleValue];
226+
lastLocation->horizontalAccuracy = [[location valueForKey:@"horizontalAccuracy"] doubleValue];
227+
lastLocation->cords = cords;
229228
}
230229

231230
if(!sendLocationTimer)
@@ -236,6 +235,10 @@ - (void)locationManager:(id)manager didUpdateLocations:(NSArray *)locations {
236235

237236
}
238237

238+
-(void)locationManager:(id)manager didFailWithError:(NSError *)error {
239+
[OneSignal onesignal_Log:ONE_S_LL_ERROR message:[NSString stringWithFormat:@"CLLocationManager did fail with error: %@", error]];
240+
}
241+
239242
+ (void)resetSendTimer {
240243
NSTimeInterval requiredWaitTime = [UIApplication sharedApplication].applicationState == UIApplicationStateActive ? foregroundSendLocationWaitTime : backgroundSendLocationWaitTime ;
241244
sendLocationTimer = [NSTimer scheduledTimerWithTimeInterval:requiredWaitTime target:self selector:@selector(sendLocation) userInfo:nil repeats:NO];

0 commit comments

Comments
 (0)