Skip to content

Commit 37a1a32

Browse files
Fix RCNConfigRealtime crash. (#14518)
Co-authored-by: Nick Cooke <36927374+ncooke3@users.noreply.github.com>
1 parent ec29695 commit 37a1a32

File tree

3 files changed

+46
-13
lines changed

3 files changed

+46
-13
lines changed

FirebaseRemoteConfig/CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
- [fixed] Codable APIs now accept optional `FirebaseDataEncoder` and
33
`FirebaseDataDecoder` parameters, allowing for customization of
44
encoding/decoding behavior. (#14368)
5+
- [fixed] Fix intermittent `RCNConfigRealtime` crash due to incorrect parsing of fragmented JSON. (#14518)
56

67
# 11.9.0
78
- [fixed] Mark internal `fetchSession` property as `atomic` to prevent a concurrency

FirebaseRemoteConfig/Sources/RCNConfigRealtime.m

Lines changed: 20 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -573,20 +573,27 @@ - (void)URLSession:(NSURLSession *)session
573573
return;
574574
}
575575

576-
NSRange endRange = [strData rangeOfString:@"}"];
577576
NSRange beginRange = [strData rangeOfString:@"{"];
578-
if (beginRange.location != NSNotFound && endRange.location != NSNotFound) {
579-
FIRLogDebug(kFIRLoggerRemoteConfig, @"I-RCN000015",
580-
@"Received config update message on stream.");
581-
NSRange msgRange =
582-
NSMakeRange(beginRange.location, endRange.location - beginRange.location + 1);
583-
strData = [strData substringWithRange:msgRange];
584-
data = [strData dataUsingEncoding:NSUTF8StringEncoding];
585-
NSDictionary *response = [NSJSONSerialization JSONObjectWithData:data
586-
options:NSJSONReadingMutableContainers
587-
error:&dataError];
588-
589-
[self evaluateStreamResponse:response error:dataError];
577+
if (beginRange.location != NSNotFound) {
578+
NSRange endRange =
579+
[strData rangeOfString:@"}"
580+
options:0
581+
range:NSMakeRange(beginRange.location + 1,
582+
strData.length - beginRange.location - 1)];
583+
if (endRange.location != NSNotFound) {
584+
FIRLogDebug(kFIRLoggerRemoteConfig, @"I-RCN000015",
585+
@"Received config update message on stream.");
586+
NSRange msgRange =
587+
NSMakeRange(beginRange.location, endRange.location - beginRange.location + 1);
588+
strData = [strData substringWithRange:msgRange];
589+
data = [strData dataUsingEncoding:NSUTF8StringEncoding];
590+
NSDictionary *response =
591+
[NSJSONSerialization JSONObjectWithData:data
592+
options:NSJSONReadingMutableContainers
593+
error:&dataError];
594+
595+
[self evaluateStreamResponse:response error:dataError];
596+
}
590597
}
591598
}
592599

FirebaseRemoteConfig/Tests/Unit/RCNRemoteConfigTest.m

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1834,6 +1834,31 @@ - (void)testFetchAndActivateRolloutsNotifyInterop {
18341834
[self waitForExpectations:@[ notificationExpectation ] timeout:_expectationTimeout];
18351835
}
18361836

1837+
- (void)testURLSessionDelegateHandlesChunkedJSON {
1838+
NSString *testString = @"} {\"testKey\":\"testValue\"}";
1839+
NSData *testData = [testString dataUsingEncoding:NSUTF8StringEncoding];
1840+
1841+
NSMutableArray<XCTestExpectation *> *expectations =
1842+
[[NSMutableArray alloc] initWithCapacity:RCNTestRCNumTotalInstances];
1843+
for (int i = 0; i < RCNTestRCNumTotalInstances; i++) {
1844+
expectations[i] = [self
1845+
expectationWithDescription:
1846+
[NSString
1847+
stringWithFormat:@"Test delegate method handling chunked JSON - instance %d", i]];
1848+
1849+
NSURLSession *networkSession = [_configFetch[i] currentNetworkSession];
1850+
NSURLSessionDataTask *dataTask = [_configFetch[i] URLSessionDataTaskWithContent:[OCMArg any]
1851+
fetchTypeHeader:[OCMArg any]
1852+
completionHandler:nil];
1853+
1854+
XCTAssertNoThrow([_configRealtime[i] URLSession:networkSession
1855+
dataTask:dataTask
1856+
didReceiveData:testData]);
1857+
[expectations[i] fulfill];
1858+
}
1859+
[self waitForExpectationsWithTimeout:_expectationTimeout handler:nil];
1860+
}
1861+
18371862
- (void)testSetCustomSignals {
18381863
NSMutableArray<XCTestExpectation *> *expectations =
18391864
[[NSMutableArray alloc] initWithCapacity:RCNTestRCNumTotalInstances];

0 commit comments

Comments
 (0)