1515 *
1616 */
1717
18- #import < Firebase/Firebase.h>
19- #import < React/RCTUtils.h>
18+ #import " RNFBFunctionsModule.h"
2019
2120#import " RNFBApp/RNFBSharedUtils.h"
22- #import " RNFBFunctionsModule.h"
21+
22+ #import < Firebase/Firebase.h>
23+ #import < React/RCTUtils.h>
2324#import < RNFBApp/RNFBRCTEventEmitter.h>
2425
2526@implementation RNFBFunctionsModule
@@ -117,8 +118,8 @@ @implementation RNFBFunctionsModule
117118 NSString *projectId = firebaseApp.options .projectID ?: @" " ;
118119 NSString *urlString;
119120 if (host != nil && port != nil ) {
120- urlString = [NSString stringWithFormat: @" http:// %@ : %@ / %@ / %@ / %@ " ,
121- host, port, projectId, customUrlOrRegion, name];
121+ urlString = [NSString
122+ stringWithFormat: @" http:// %@ : %@ / %@ / %@ / %@ " , host, port, projectId, customUrlOrRegion, name];
122123 } else {
123124 urlString = [NSString stringWithFormat: @" https://%@ -%@ .cloudfunctions.net/%@ " ,
124125 customUrlOrRegion, projectId, name];
@@ -150,60 +151,61 @@ @implementation RNFBFunctionsModule
150151 config.URLCache = nil ;
151152 NSURLSession *session = [NSURLSession sessionWithConfiguration: config];
152153
153- NSURLSessionDataTask *task =
154- [session dataTaskWithRequest: request
155- completionHandler: ^(NSData *data, NSURLResponse *response, NSError *error) {
156- if (error) {
157- NSMutableDictionary *body = [@{@" error" : error.localizedDescription ?: @" error" } mutableCopy];
158- [RNFBSharedUtils sendJSEventForApp: firebaseApp
159- name: RNFB_FUNCTIONS_STREAMING_EVENT
160- body: @{
161- @" listenerId" : listenerId,
162- @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
163- @" body" : body
164- }];
165- } else if ([response isKindOfClass: [NSHTTPURLResponse class ]] &&
166- [(NSHTTPURLResponse *)response statusCode ] >= 400 ) {
167- NSHTTPURLResponse *http = (NSHTTPURLResponse *)response;
168- NSString *msg = [NSString stringWithFormat: @" http_error_%ld _%@ " ,
169- (long )http.statusCode,
170- [NSHTTPURLResponse localizedStringForStatusCode: http.statusCode]];
171- NSMutableDictionary *body = [@{@" error" : msg} mutableCopy];
172- [RNFBSharedUtils sendJSEventForApp: firebaseApp
173- name: RNFB_FUNCTIONS_STREAMING_EVENT
174- body: @{
175- @" listenerId" : listenerId,
176- @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
177- @" body" : body
178- }];
179- } else if (data.length > 0 ) {
180- NSString *payload = [[NSString alloc ] initWithData: data encoding: NSUTF8StringEncoding];
181- // Split into lines (handles SSE or NDJSON)
182- [payload enumerateLinesUsingBlock: ^(NSString *line, BOOL *stop) {
183- if (line.length == 0 ) return ;
184- NSString *trimmed = [line hasPrefix: @" data: " ] ? [line substringFromIndex: 6 ] : line;
185- NSMutableDictionary *body = [@{@" text" : trimmed} mutableCopy];
186- [RNFBSharedUtils sendJSEventForApp: firebaseApp
187- name: RNFB_FUNCTIONS_STREAMING_EVENT
188- body: @{
189- @" listenerId" : listenerId,
190- @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
191- @" body" : body
192- }];
193- }];
194- }
195- // Always emit done at end
196- [RNFBSharedUtils sendJSEventForApp: firebaseApp
197- name: RNFB_FUNCTIONS_STREAMING_EVENT
198- body: @{
199- @" listenerId" : listenerId,
200- @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
201- @" body" : @{@" done" : @YES }
202- }];
203- @synchronized (httpsCallableStreamListeners) {
204- [httpsCallableStreamListeners removeObjectForKey: listenerId];
205- }
206- }];
154+ NSURLSessionDataTask *task = [session
155+ dataTaskWithRequest: request
156+ completionHandler: ^(NSData *data, NSURLResponse *response, NSError *error) {
157+ if (error) {
158+ NSMutableDictionary *body =
159+ [@{@" error" : error.localizedDescription ?: @" error" } mutableCopy];
160+ [RNFBSharedUtils sendJSEventForApp: firebaseApp
161+ name: RNFB_FUNCTIONS_STREAMING_EVENT
162+ body: @{
163+ @" listenerId" : listenerId,
164+ @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
165+ @" body" : body
166+ }];
167+ } else if ([response isKindOfClass: [NSHTTPURLResponse class ]] &&
168+ [(NSHTTPURLResponse *)response statusCode ] >= 400 ) {
169+ NSHTTPURLResponse *http = (NSHTTPURLResponse *)response;
170+ NSString *msg = [NSString
171+ stringWithFormat: @" http_error_%ld _%@ " , (long )http.statusCode,
172+ [NSHTTPURLResponse localizedStringForStatusCode: http.statusCode]];
173+ NSMutableDictionary *body = [@{@" error" : msg} mutableCopy];
174+ [RNFBSharedUtils sendJSEventForApp: firebaseApp
175+ name: RNFB_FUNCTIONS_STREAMING_EVENT
176+ body: @{
177+ @" listenerId" : listenerId,
178+ @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
179+ @" body" : body
180+ }];
181+ } else if (data.length > 0 ) {
182+ NSString *payload = [[NSString alloc ] initWithData: data encoding: NSUTF8StringEncoding];
183+ // Split into lines (handles SSE or NDJSON)
184+ [payload enumerateLinesUsingBlock: ^(NSString *line, BOOL *stop) {
185+ if (line.length == 0 ) return ;
186+ NSString *trimmed = [line hasPrefix: @" data: " ] ? [line substringFromIndex: 6 ] : line;
187+ NSMutableDictionary *body = [@{@" text" : trimmed} mutableCopy];
188+ [RNFBSharedUtils sendJSEventForApp: firebaseApp
189+ name: RNFB_FUNCTIONS_STREAMING_EVENT
190+ body: @{
191+ @" listenerId" : listenerId,
192+ @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
193+ @" body" : body
194+ }];
195+ }];
196+ }
197+ // Always emit done at end
198+ [RNFBSharedUtils sendJSEventForApp: firebaseApp
199+ name: RNFB_FUNCTIONS_STREAMING_EVENT
200+ body: @{
201+ @" listenerId" : listenerId,
202+ @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
203+ @" body" : @{@" done" : @YES }
204+ }];
205+ @synchronized (httpsCallableStreamListeners) {
206+ [httpsCallableStreamListeners removeObjectForKey: listenerId];
207+ }
208+ }];
207209
208210 @synchronized (httpsCallableStreamListeners) {
209211 httpsCallableStreamListeners[listenerId] = task;
@@ -229,7 +231,7 @@ @implementation RNFBFunctionsModule
229231 if (!httpsCallableStreamListeners) {
230232 httpsCallableStreamListeners = [NSMutableDictionary dictionary ];
231233 }
232-
234+
233235 // Use the provided URL directly
234236 NSURLComponents *components = [NSURLComponents componentsWithString: url];
235237 if (components == nil ) {
@@ -243,14 +245,14 @@ @implementation RNFBFunctionsModule
243245 }];
244246 return ;
245247 }
246-
248+
247249 // Override to emulator if provided
248250 if (host != nil && port != nil ) {
249251 components.scheme = @" http" ;
250252 components.host = host;
251253 components.port = port;
252254 }
253-
255+
254256 NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL: [components URL ]];
255257 [request setHTTPMethod: @" GET" ];
256258 [request setValue: @" text/event-stream, application/x-ndjson, */*" forHTTPHeaderField: @" Accept" ];
@@ -260,60 +262,61 @@ @implementation RNFBFunctionsModule
260262 config.URLCache = nil ;
261263 NSURLSession *session = [NSURLSession sessionWithConfiguration: config];
262264
263- NSURLSessionDataTask *task =
264- [session dataTaskWithRequest: request
265- completionHandler: ^(NSData *data, NSURLResponse *response, NSError *error) {
266- if (error) {
267- NSMutableDictionary *body = [@{@" error" : error.localizedDescription ?: @" error" } mutableCopy];
268- [RNFBSharedUtils sendJSEventForApp: firebaseApp
269- name: RNFB_FUNCTIONS_STREAMING_EVENT
270- body: @{
271- @" listenerId" : listenerId,
272- @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
273- @" body" : body
274- }];
275- } else if ([response isKindOfClass: [NSHTTPURLResponse class ]] &&
276- [(NSHTTPURLResponse *)response statusCode ] >= 400 ) {
277- NSHTTPURLResponse *http = (NSHTTPURLResponse *)response;
278- NSString *msg = [NSString stringWithFormat: @" http_error_%ld _%@ " ,
279- (long )http.statusCode,
280- [NSHTTPURLResponse localizedStringForStatusCode: http.statusCode]];
281- NSMutableDictionary *body = [@{@" error" : msg} mutableCopy];
282- [RNFBSharedUtils sendJSEventForApp: firebaseApp
283- name: RNFB_FUNCTIONS_STREAMING_EVENT
284- body: @{
285- @" listenerId" : listenerId,
286- @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
287- @" body" : body
288- }];
289- } else if (data.length > 0 ) {
290- NSString *payload = [[NSString alloc ] initWithData: data encoding: NSUTF8StringEncoding];
291- // Split into lines (handles SSE or NDJSON)
292- [payload enumerateLinesUsingBlock: ^(NSString *line, BOOL *stop) {
293- if (line.length == 0 ) return ;
294- NSString *trimmed = [line hasPrefix: @" data: " ] ? [line substringFromIndex: 6 ] : line;
295- NSMutableDictionary *body = [@{@" text" : trimmed} mutableCopy];
296- [RNFBSharedUtils sendJSEventForApp: firebaseApp
297- name: RNFB_FUNCTIONS_STREAMING_EVENT
298- body: @{
299- @" listenerId" : listenerId,
300- @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
301- @" body" : body
302- }];
303- }];
304- }
305- // Always emit done at end
306- [RNFBSharedUtils sendJSEventForApp: firebaseApp
307- name: RNFB_FUNCTIONS_STREAMING_EVENT
308- body: @{
309- @" listenerId" : listenerId,
310- @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
311- @" body" : @{@" done" : @YES }
312- }];
313- @synchronized (httpsCallableStreamListeners) {
314- [httpsCallableStreamListeners removeObjectForKey: listenerId];
315- }
316- }];
265+ NSURLSessionDataTask *task = [session
266+ dataTaskWithRequest: request
267+ completionHandler: ^(NSData *data, NSURLResponse *response, NSError *error) {
268+ if (error) {
269+ NSMutableDictionary *body =
270+ [@{@" error" : error.localizedDescription ?: @" error" } mutableCopy];
271+ [RNFBSharedUtils sendJSEventForApp: firebaseApp
272+ name: RNFB_FUNCTIONS_STREAMING_EVENT
273+ body: @{
274+ @" listenerId" : listenerId,
275+ @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
276+ @" body" : body
277+ }];
278+ } else if ([response isKindOfClass: [NSHTTPURLResponse class ]] &&
279+ [(NSHTTPURLResponse *)response statusCode ] >= 400 ) {
280+ NSHTTPURLResponse *http = (NSHTTPURLResponse *)response;
281+ NSString *msg = [NSString
282+ stringWithFormat: @" http_error_%ld _%@ " , (long )http.statusCode,
283+ [NSHTTPURLResponse localizedStringForStatusCode: http.statusCode]];
284+ NSMutableDictionary *body = [@{@" error" : msg} mutableCopy];
285+ [RNFBSharedUtils sendJSEventForApp: firebaseApp
286+ name: RNFB_FUNCTIONS_STREAMING_EVENT
287+ body: @{
288+ @" listenerId" : listenerId,
289+ @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
290+ @" body" : body
291+ }];
292+ } else if (data.length > 0 ) {
293+ NSString *payload = [[NSString alloc ] initWithData: data encoding: NSUTF8StringEncoding];
294+ // Split into lines (handles SSE or NDJSON)
295+ [payload enumerateLinesUsingBlock: ^(NSString *line, BOOL *stop) {
296+ if (line.length == 0 ) return ;
297+ NSString *trimmed = [line hasPrefix: @" data: " ] ? [line substringFromIndex: 6 ] : line;
298+ NSMutableDictionary *body = [@{@" text" : trimmed} mutableCopy];
299+ [RNFBSharedUtils sendJSEventForApp: firebaseApp
300+ name: RNFB_FUNCTIONS_STREAMING_EVENT
301+ body: @{
302+ @" listenerId" : listenerId,
303+ @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
304+ @" body" : body
305+ }];
306+ }];
307+ }
308+ // Always emit done at end
309+ [RNFBSharedUtils sendJSEventForApp: firebaseApp
310+ name: RNFB_FUNCTIONS_STREAMING_EVENT
311+ body: @{
312+ @" listenerId" : listenerId,
313+ @" eventName" : RNFB_FUNCTIONS_STREAMING_EVENT,
314+ @" body" : @{@" done" : @YES }
315+ }];
316+ @synchronized (httpsCallableStreamListeners) {
317+ [httpsCallableStreamListeners removeObjectForKey: listenerId];
318+ }
319+ }];
317320
318321 @synchronized (httpsCallableStreamListeners) {
319322 httpsCallableStreamListeners[listenerId] = task;
0 commit comments