I have a Flutter application in production that is using Firebase cloud function for the backend and sometimes it throws some FirebaseFunctionsException INTERNAL errors for one particular function but without much information on the client side.
The weird thing is that I don't even have information on the console side, if I look at the logs I don't see any call to the function... I tried to put minInstance to the cloud function but I still have the error.
The particularity of the function where I have the error is that it's called by ~40 users at the same time, some have an error, some do not...
Is someone know how I can find out what is going on?
edit: Here is the front-end stacktrace I got. No trace on the cloud function logs.
FirebaseFunctionsException
[firebase_functions/internal] INTERNAL
#0 StandardMethodCodec.decodeEnvelope (package:flutter/src/services/message_codecs.dart:653)
#1 MethodChannel._invokeMethod (package:flutter/src/services/platform_channel.dart:296)
<asynchronous suspension>
#2 MethodChannelHttpsCallable.call (package:cloud_functions_platform_interface/src/method_channel/method_channel_https_callable.dart:23)
<asynchronous suspension>
#3 HttpsCallable.call (package:cloud_functions/src/https_callable.dart:49)
<asynchronous suspension>
Try add a timeout to the call to the cloud function. Example:
final HttpsCallable callable = FirebaseFunctions.instance.httpsCallable('yourFunctionName');
final HttpsCallableResult result = await callable.call(<String, dynamic>{
'param1': 'value1',
'param2': 'value2',
}).timeout(Duration(seconds: 10));
print(result.data);
Explanation: timeout is a method of Future class, so you can use it on the result of the call to the cloud function. If the cloud function takes more than 10 seconds to return, the timeout will throw an exception. You can then catch that exception and handle it.
Related
W/GoogleApiManager( 1448): The service for com.google.firebase.dynamiclinks.internal.DynamicLinksClient is not available: ConnectionResult{statusCode=SERVICE_INVALID, resolution=null, message=null}
E/flutter ( 1448): [ERROR:flutter/lib/ui/ui_dart_state.cc(209)] Unhandled Exception: [firebase_dynamic_links/unknown] com.google.android.gms.common.api.ApiException: 17: API: DynamicLinks.API is not available on this device. Connection failed with: ConnectionResult{statusCode=SERVICE_INVALID, resolution=null, message=null}
E/flutter ( 1448):
I had followed the exact steps given in https://firebase.flutter.dev/docs/dynamic-links/usage
Make sure, that your device have google services.
For emulator: create one with play store icon.
For physical device make sure that this device is not in banned from google lists. For example Huawei devices.
based on this issues: https://github.com/firebase/flutterfire/issues/8397
I'm running a query which requires creation of composite index. AFAIK, there are two ways of going around it.
Go to the console and manually create the index.
Run the query as it is to receive an error in the console which can direct me to the Firebase console after creating the index.
But I'm not seeing any such links on the console. Here's the query:
collection.where('foo', isEqualTo: 'bar').where('baz', isLessThan: 1);
Error:
E/flutter (21010): [ERROR:flutter/lib/ui/ui_dart_state.cc(207)] Unhandled Exception: [cloud_firestore/failed-precondition] Operation was rejected because the system is not in a state required for the operation's execution. If performing a query, ensure it has been indexed via the Firebase console.
E/flutter (21010): #0 MethodChannelQuery.get (package:cloud_firestore_platform_interface/src/method_channel/method_channel_query.dart:108:7)
E/flutter (21010): <asynchronous suspension>
E/flutter (21010): #1 _JsonQuery.get (package:cloud_firestore/src/query.dart:385:9)
E/flutter (21010): <asynchronous suspension>
E/flutter (21010): #2 _FooPageState.fooMethod (package:foo_bar_baz.dart:140:27)
E/flutter (21010): <asynchronous suspension>
E/flutter (21010):
W/Firestore(21010): (23.0.0) [WatchStream]: (602e2ef) Stream closed with status: Status{code=CANCELLED, description=Disconnecting idle stream. Timed out waiting for new targets., cause=null}.
Apparently Firebase has stopped returning the index creation link in client SDKs. You can still use the Admin SDK in a Cloud Function to get direct index creation link or create one yourself manually as shown:
Make sure you replace the collection and fields names with the original names.
I use Flutter, Timer and Firebase/Firestore.batch to do something like this sample code to save data periodically on Mac.
https://github.com/tomoyuki28jp/flutterfire_scheduled_batch_write_sample2
When I run my app for few days, I get this error randomly:
flutter: [cloud_firestore/permission-denied] The caller does not have permission to execute the specified operation.
flutter:
#0 MethodChannelWriteBatch.commit
package:cloud_firestore_platform_interface/…/method_channel/method_channel_write_batch.dart:51
<asynchronous suspension>
After hot reloading, it start working again.
Background task keep throwing this error until restarting or reloading my app
While a background task is throwing this error, I can still successfully save firestore data by using my app UI manually.
How can I investigate the cause?
User credentials do expire over time - hot reloading likely re-establishes the Auth session. It is known that Auth needs to be re-established periodically - Firestore is NOT really intended as a permanent connection. Your code needs to be able to respond to changes in Auth state (there is a library function to Listen to Auth events), and respond accordingly - including re-authorizing if that's your intent.
I have one project that I have to sell to another clients, so I wanna found a way to unify the code to, when I release some updates, I have to manipulate only one code (and, of course, keeping the specificities from each one)
The problem is In my first app I was using firebase_messaging with its google-services.json. But in this new client I won't use it... I tried to run and it throws this error:
E/flutter ( 7850): [ERROR:flutter/lib/ui/ui_dart_state.cc(186)] Unhandled Exception: [core/not-initialized] Firebase has not been correctly initialized. Have you added the "google-services.json" file to the project?
E/flutter ( 7850):
E/flutter ( 7850): View the Android Installation documentation for more information: https://firebase.flutter.dev/docs/installation/android
E/flutter ( 7850):
E/flutter ( 7850): #0 MethodChannelFirebase.initializeApp (package:firebase_core_platform_interface/src/method_channel/method_channel_firebase.dart:86:9)
E/flutter ( 7850): <asynchronous suspension>
E/flutter ( 7850): #1 Firebase.initializeApp (package:firebase_core/src/firebase.dart:44:9)
E/flutter ( 7850): <asynchronous suspension>
E/flutter ( 7850): #2 main (package:app_md/main.dart:72:3)
E/flutter ( 7850): <asynchronous suspension>
E/flutter ( 7850):
How can I deal with child projects that don't will use firebase_messaging:? I'm using the 'config' parameter to do this heritage
I used this way: https://medium.com/#ramiechaarani/how-to-make-a-white-label-app-in-flutter-6c3ea40fd7d5
In sum:
I have One main app that initially I did to one client. This client uses firebase. Now I wanna keep only the main functions and separate it to use in another client. The problem is, this new client does not use firebase, so when i try to run the app it throws that error because I haven't a google-services.json. How can I say that in this project (which inherit the main project) I don't will use firebase?
Expected outcome: in the second brand app don't use firebase..
maybe there is a way to override dependencies? Or there is another approach to achieve my goal..
Extract a common module containing only client interface with common methods
Add the implementation to clients' modules (or create module per
implementation, depends if multiple clients are going to use the
same implementation)
In your 'core' (white label) module's entrypoint add the interface from step 1 as a parameter
In client's module, pass the implementation as a parameter to the entrypoint
This is essentially what Separation of conerns is about. Your BLOCs (or whatever you're using to do business logic) needn't to know where 'stuff' is coming from. All they care about is the fact that 'stuff' comes.
In order to better understand SoC, you might want to read something more easygoing than the Wikipedia article, for example: How do you explain Separation of Concerns to others?
I'm facing the same problem as this guy question
But his accepted answer didn't helped me.
The problem:
When an user signs out, and another different user signs in, all data shown on my app is from the previous signed out user due to firebase caching system. I searched about this issue and found a solution that consists in calling this method:
FirebaseFirestore.instance.clearPersistence();
But everytime and everywhere I place this line of code, throws an exception saying I cannot call this method when the client is running:
Exception has occurred.
PlatformException (PlatformException(failed-precondition, Operation was rejected because the system is not in a state required for the operation's execution. If performing a query, ensure it has been indexed via the Firebase console., {code: failed-precondition, message: Operation was rejected because the system is not in a state required for the operation's execution. If performing a query, ensure it has been indexed via the Firebase console., nativeErrorMessage: Persistence cannot be cleared while the client is running., nativeErrorCode: 9}))
so, how to call this method? or better, is there a best way to solve this problem?
It seems it's necessary to terminate the FirebaseFirestore.instance first.
At the end of my log off method I call:
await FirebaseFirestore.instance.terminate();
await FirebaseFirestore.instance.clearPersistence();
I get no errors thrown and everything seems to be working as it should now.
You should call it immediately after you initialize Firebase, and before you make the first query.
add this to your Login Button 'onPressed':
FirebaseFirestore.instance.terminate();
FirebaseFirestore.instance
.clearPersistence()
.then((value) => signinUser(email, password, context));