firebase / firebase-admin-java Goto Github PK
View Code? Open in Web Editor NEWFirebase Admin Java SDK
Home Page: https://firebase.google.com/docs/admin/setup
License: Apache License 2.0
Firebase Admin Java SDK
Home Page: https://firebase.google.com/docs/admin/setup
License: Apache License 2.0
I just ran into a strange bug in some geofire-java testing that has been fixed in the Android SDK but is not fixed here.
Internal details:
@schmidt-sebastian fixed it in CL 141802441, the internal bug number is 32519140.
I have posted issues for functionality firebase cloud messaging in StackOverflow https://stackoverflow.com/questions/47569891/condition-topic-is-case-sensitive-condition-or-not-working
Admin SDK uses Google Java HTTP client to make outbound HTTP connections. But we currently do not set the connection and read timeout for outbound requests. These need to be configurable via FirebaseOptions
or a similar API.
Now that 5.4.0 deprecated Task etc. I'm not sure how to replace TaskCompletionSource? Are there any examples how to implement behavior like this:
private Task<List<String>> getWorkUrisTask() {
final TaskCompletionSource<List<String>> tcs = new TaskCompletionSource<>();
firebaseService.getReference("/w").addListenerForSingleValueEvent(new ValueEventListener() {
@Override
public void onDataChange(final DataSnapshot ds) {
try {
final List<String> workUris = new ArrayList<>();
if (ds != null && ds.exists()) {
for (final DataSnapshot child : ds.getChildren()) {
if (checkAllImagesAreReady(child)) {
final String workUri = child.child("w").getValue(String.class);
workUris.add(workUri);
}
}
}
tcs.setResult(workUris);
} catch (Exception e) {
tcs.setException(e);
}
}
@Override
public void onCancelled(DatabaseError de) {
tcs.setException(de);
}
});
return tcs.getTask();
}
Right now it's not possible to create custom JWT token with firebase-admin SDK on Java and this leads to the problems of credentials confidentiality.
The most efficient way to obtain credentials while you're on AppEngine or GCE - obtain them via GoogleCredential.getApplicationDefault()
, or in case of Firebase - FirebaseCredentials.applicationDefault()
, but FirebaseAuth.createToken
lacks support for this type of credentials.
Implementing application default credentials support for custom JWT tokens will help people not to save their credentials in the VCS or gamble with cumbersome environment variables.
Hello,
An issue was filed against google-cloud-java ( googleapis/google-cloud-java#2890 ) because users are having trouble with version consistency. It turns out that firebase-admin added types from google-cloud-java onto its surface in this PR:
Since google-cloud-firestore is beta, this means that firebase-admin is now exposing unstable types on its surface, which could break users between minor versions despite any promises of API stability within this repo.
When I try to serialize a LocalDate
I get the following exception.
com.google.firebase.database.DatabaseException: Found conflicting getters for name: getChronology
at com.google.firebase.database.utilities.encoding.CustomClassMapper$BeanMapper.<init>(CustomClassMapper.java:476) ~[classes/:na]
at com.google.firebase.database.utilities.encoding.CustomClassMapper.loadOrCreateBeanMapperForClass(CustomClassMapper.java:324) ~[classes/:na]
at com.google.firebase.database.utilities.encoding.CustomClassMapper.serialize(CustomClassMapper.java:168) ~[classes/:na]
at com.google.firebase.database.utilities.encoding.CustomClassMapper.access$2(CustomClassMapper.java:117) ~[classes/:na]
at com.google.firebase.database.utilities.encoding.CustomClassMapper$BeanMapper.serialize(CustomClassMapper.java:806) ~[classes/:na]
at com.google.firebase.database.utilities.encoding.CustomClassMapper.serialize(CustomClassMapper.java:169) ~[classes/:na]
at com.google.firebase.database.utilities.encoding.CustomClassMapper.access$2(CustomClassMapper.java:117) ~[classes/:na]
at com.google.firebase.database.utilities.encoding.CustomClassMapper$BeanMapper.serialize(CustomClassMapper.java:806) ~[classes/:na]
at com.google.firebase.database.utilities.encoding.CustomClassMapper.serialize(CustomClassMapper.java:169) ~[classes/:na]
at com.google.firebase.database.utilities.encoding.CustomClassMapper.serialize(CustomClassMapper.java:143) ~[classes/:na]
at com.google.firebase.database.utilities.encoding.CustomClassMapper.convertToPlainJavaTypes(CustomClassMapper.java:68) ~[classes/:na]
at com.google.firebase.database.DatabaseReference.setValueInternal(DatabaseReference.java:321) ~[classes/:na]
at com.google.firebase.database.DatabaseReference.setValue(DatabaseReference.java:229) ~[classes/:na]
at com.google.firebase.database.DatabaseReference.setValueAsync(DatabaseReference.java:180) ~[classes/:na]
The cause is, that LocalDate
overrides the java.time.chrono.ChronoLocalDate.getChronology()
method which returns a java.time.chrono.Chronology
. The override returns java.time.chrono.IsoChronology
which is an implementation of the original return type.
Question: how can such overrides be addressed in the future that such classes (available in core Java or other libraries without access) can be serialized? If we can figure this out, I am happy to create a PR with the implementation.
How can we know that all offline data synchronized after goOnline, i need to ensure that all data synchronized before clear the data
Is there a gradle repo to access the last snapshot ? (5.0.2)
Set the X-CLIENT-VERSION
header on HTTP calls to user management REST API.
Equivalent logic in Admin Node.js SDK: https://github.com/firebase/firebase-admin-node/blob/master/src/auth/auth-api-request.ts#L37
It would be really nice to have feature parity with node-admin, that has these tools to manage users.
I just upgraded to 5.6.0 version to try custom claims and now I can't get user because I get NoSuchMethodError
Exception in thread "firebase-default-0" java.lang.NoSuchMethodError: org.json.JSONObject.toMap()Ljava/util/Map;
at com.google.firebase.auth.UserRecord.<init>(UserRecord.java:85)
at com.google.firebase.auth.FirebaseUserManager.getUserById(FirebaseUserManager.java:112)
at com.google.firebase.auth.FirebaseAuth$3.call(FirebaseAuth.java:266)
at com.google.firebase.auth.FirebaseAuth$3.call(FirebaseAuth.java:263)
at com.google.firebase.tasks.Tasks$1.run(Tasks.java:82)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
at java.lang.Thread.run(Thread.java:748)
So what I did.
I wanted to keep previous claims so I created copy of map and add new key-val.
@Override
public void addUserCustomClaims(final String userId, String key, String val) {
final UserRecord user = getUser(userId);
final Map<String, Object> customClaims = new HashMap<>(user.getCustomClaims());
customClaims.put(key, val);
final Void aVoid = Single.fromFuture(
firebaseAuth.setCustomUserClaimsAsync(userId, customClaims))
.blockingGet();
}
It was inserted as I see but now I can't get user because it's throwing exception.
With breakpoint set to
customClaims={"u_type":"USER"}
this.customClaims=null
Hello,
When a response comes back with an erred status code com.google.firebase.messaging.FirebaseMessaging#handleSendHttpError attempts to read the body, however if the content is null, the jsonFactory throws a NullPointerException, which is not converted into a FirebaseMessagingException. This ends up hiding the http response code.
In the tests, there is a test for testSendError, but there is no test that uses .setZeroContent() which will expose the problem.
To reproduce, send a mock response with an error status code and no content.
I was looking for hours why getValue doesn't return anything. The thread dies in the background silently. First as i step debug the code i've seen that some things must be present in the pojos like empty constructor and getters at least. I don't know why the exception is swallowed. I just can assume that google endpoints hide it from my eyes. I am using firebase with cloud endpoints together.
Work is currently underway in the Node Admin SDK to implement phone auth support (see branch). This needs to be ported to the Java Admin SDK. This will provide:
My Environment:
Please provide Firebase analytics Api for server side. We would like to give a decision right now and being limited on client side is unfortunately not acceptable.
Transaction.Handler.onComplete() exceptions are swallowed, I think by ThreadPoolEventTarget. It would be nice if they were logged. I spent a lot of time thinking that onComplete() wasn't being called at all.
Run a transaction. Throw an exception in Transaction.Handler.onComplete(). It is not logged.
// kotlin, but should work in java too
override fun onComplete(databaseError: DatabaseError?, committed: Boolean, dataSnapshot: DataSnapshot?) {
CLog.i("Transaction completed")
if (true) throw IllegalStateException("this won't be logged");
}
FirebaseTokenVerifier
should extend IdTokenVerifier
.auth
package, and made package-protected.I implemented the sign in flow which is described here: https://firebase.google.com/docs/auth/web/facebook-login (see point Handling account-exists-with-different-credential Errors).
If a user tries to sign up with an email which is already used in an account of a different provider, he is offered to link his accounts. This works well for the web SDK.
When I tried to do the same with the android SDK I noticed that the error object FirebaseAuthUserCollisionException
provides no information about which email it is that is already used. That makes it impossible to handle account-exists-with-different-credential
errors with the android SDK.
I implemented the same with the iOS SDK and even though there the credential is not attached to the corresponding FIRAuthErrorCodeEmailAlreadyInUse
object, at least the email address is. The credential can be stored by the developer and retrieved from elsewhere s.t. the error can be dealt with in iOS too.
Only in android a developer has no chance to know which email address is duplicate and therefore you can't even let the user know and have to display a generic error message like 'email address is already in use' which leads to poor usability in my opinion.
FirebaseAuthUserCollisionException
should be thrown and the email address can't be retrievedUnder some circumstances Firebase SDK squashes updates from different transactions into single set operation which wipes out existing data.
I have a structure like this:
/test/users/u1/
lastUpdate: 123
calls/history
c1
c2
c3
In my code I do the following:
At the end I have calls/history with call c4 only. Calls c1, c2, c3 were wiped out.
I have created demo repository which demonstrates the problem: https://github.com/sergey-ua/firebase-transaction-issue-demo
./mvnw -Dtest=FirebaseTransactionsTest#resetState -DdatabaseUrl="https://your-db-url.firebaseio.com/" -Dcert="path/to/cert.json" test
./mvnw -Dtest=FirebaseTransactionsTest#subsequentTransactions -DdatabaseUrl="https://your-db-url.firebaseio.com/" -Dcert="path/to/cert.json" test
See full code here:
https://github.com/sergey-ua/firebase-transaction-issue-demo/blob/master/src/test/java/org/test/firebase/FirebaseTransactionsTest.java
firebase-transaction-log.log
See Firebase SDK logs attached.
Copied code snippet is here:
@Test
/**
* Run this to reproduce issue. This test will fail
* ./mvnw -Dtest=FirebaseTransactionsTest#subsequentTransactions -DdatabaseUrl="https://your-db-url.firebaseio.com/" -Dcert="/path/to/serviceAccountKey.json" test
*/
public void subsequentTransactions() throws Exception {
CountDownLatch latch = new CountDownLatch(3);
String callUid = UUID.randomUUID().toString();
//create new call
firebaseDatabase.getReference(TEST_USER_PATH).child("calls").child("history").child(callUid)
.runTransaction(new Transaction.Handler() {
@Override
public Transaction.Result doTransaction(MutableData currentData) {
currentData.child("/").setValue(getCallTemplate("updated"));
return Transaction.success(currentData);
}
@Override
public void onComplete(DatabaseError error, boolean committed, DataSnapshot currentData) {
latch.countDown();
}
});
//update call we have just created
firebaseDatabase.getReference(TEST_USER_PATH).child("calls").child("history").child(callUid)
.runTransaction(new Transaction.Handler() {
@Override
public Transaction.Result doTransaction(MutableData currentData) {
currentData.child("/").setValue(getCallTemplate("updated"));
return Transaction.success(currentData);
}
@Override
public void onComplete(DatabaseError error, boolean committed, DataSnapshot currentData) {
latch.countDown();
}
});
//Thread.sleep(5000); <- uncomment this and test will pass
//update user object
firebaseDatabase.getReference(TEST_USER_PATH).runTransaction(new Transaction.Handler() {
@Override
public Transaction.Result doTransaction(MutableData currentData) {
currentData.child("lastUpdated").setValue(new Date().getTime());
return Transaction.success(currentData);
}
@Override
public void onComplete(DatabaseError error, boolean committed, DataSnapshot currentData) {
latch.countDown();
}
});
latch.await();
//lets check initial calls are in place
assertUserObject();
}
Hello!
When I trying to get some info from the database and the query contains some of startAt, endAt, equalTo the query hangs and the thread keeps workings and my method cant return anything...
Event Listeners removed for simplicity, can be reproduced with or without them
example: only the String "before query" is printed, then the nothing happens, it hangs
FirebaseDatabase db = FirebaseDatabase.getInstance();
System.out.println("before query");
db.getReference("/some/path/").orderByChild("pending").equalTo(true);
System.out.println("after query");
But, if I remove the "equalTo" condition the mehtod executes normally
example: both strings are printed and the data is retreived without any problem.
FirebaseDatabase db = FirebaseDatabase.getInstance();
System.out.println("before query");
db.getReference("/some/path/").orderByChild("pending");
System.out.println("after query");
edit: I don't know if this is useful, but if I try the same query on the node.js enviroment it works and my data is retrieved without any problem
URL:
https://us-central1-ossbot-f0cad.cloudfunctions.net/githubWebhook
Content type:
application/json
Secret:
N/A
Select individual events:
Hi guys,
We need to operate in a corporate environment that severely restricts access to the wider internet. Trying to white-label all googleapis.com IPs is a fools errand (there are a lot of them, and likely to change).
The best way would be allow us to control the prefix of the URLs to googleapis.com calls so that for example we can direct them via a https://googleapis.example.com/ proxy that is under out control.
This is a big problem for us right now as we are at the point where we're trying to deploy this in production for a very large client and we've hit a wall on how we can get this done.
Thank you!
Add support to the Firebase Admin SDK for any Collection - they all provide an iterator()
so I don't see why it is a problem to do this.
I am trying to serialize a Set using Firebase and it is throwing Serializing Collections is not supported, please use Lists instead
due to this throw statement
Attempt to serialize a Set with the Firebase Admin SDK
Here is a JUnit 4.0 test that produces the error:
import com.google.firebase.database.DatabaseException;
import com.google.firebase.database.utilities.encoding.CustomClassMapper;
import org.junit.Test;
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
import static org.junit.Assert.assertEquals;
public class FirebaseTest {
@Test
public void firebaseCannotSerializeSets() throws Exception {
Map<String, Object> data = new HashMap<>();
data.put("myset", Collections.singleton("1"));
try {
CustomClassMapper.convertToPlainJavaTypes(data);
} catch (DatabaseException e) {
assertEquals("Serializing Collections is not supported, " +
"please use Lists instead", e.getMessage());
}
}
}
This is more a request, can Google create a role so only read is allowed for a Service Account?
Please see https://stackoverflow.com/questions/48218045/firebase-limited-service-account
After app.delete(), there is still dangling thread. Bug can be reproduced on both 5.2.0 and latest 5.3.1 releases.
Run a trivial task, such as getUser, and call app.delete() after task complete. In my IDE, I observed three threads were created: pool-2-thread-1, pool-2-thread-2, pool-3-thread-1. After a while, pool-2-thread-[1,2] exited but pool-3-thread-1 is still dangling.
A trivial java test program
app = FirebaseApp.initializeApp(options);
Task<UserRecord> task = auth.getUser(uid);
task.addOnCompleteListener(new OnCompleteListener<UserRecord>() {
@Override
public void onComplete(Task<UserRecord> task) {
app.delete();
}
});
Test program won't exit after task completed.
Looks like TokenRefresher was not exiting. I have to add this hack after app.delete() call:
FirebaseExecutors.DEFAULT_SCHEDULED_EXECUTOR.shutdown();
My app starts up and then listens for changes to my Firebase Database. I am running my app in Google App Engine, and have recently been getting lots of the following errors:
“The process handling this request unexpectedly died. This is likely to cause a new process to be used for the next request to your application. (Error code 203)” These errors occur every 30 minutes or so, and the App restarts, even if there are no changes to the database.
In an attempt to debug this, I have been running my app locally, but I always get the following error on initialising and then obtaining the reference to my Firebase Database:
[FirebaseDatabaseWorker] ERROR com.google.firebase.database.core.RunLoop - Uncaught exception in Firebase Database runloop (5.11.0). Please report to [email protected]
java.lang.NoClassDefFoundError: java.nio.channels.spi.SelectorProvider is a restricted class. Please see the Google App Engine developer's guide for more details.
at com.google.appengine.tools.development.agent.runtime.Runtime.reject(Runtime.java:50)
at io.netty.channel.nio.NioEventLoopGroup.(NioEventLoopGroup.java:63)
at com.google.firebase.database.connection.NettyWebSocketClient.(NettyWebSocketClient.java:72)
at com.google.firebase.database.connection.WebsocketConnection$DefaultWSClientFactory.newClient(WebsocketConnection.java:435)
at com.google.firebase.database.connection.WebsocketConnection.(WebsocketConnection.java:80)
at com.google.firebase.database.connection.WebsocketConnection.(WebsocketConnection.java:68)
at com.google.firebase.database.connection.Connection$DefaultWebsocketConnectionFactory.newConnection(Connection.java:297)
at com.google.firebase.database.connection.Connection.(Connection.java:72)
at com.google.firebase.database.connection.Connection.(Connection.java:57)
at com.google.firebase.database.connection.PersistentConnectionImpl$DefaultConnectionFactory.newConnection(PersistentConnectionImpl.java:1303)
at com.google.firebase.database.connection.PersistentConnectionImpl.openNetworkConnection(PersistentConnectionImpl.java:547)
at com.google.firebase.database.connection.PersistentConnectionImpl.access$800(PersistentConnectionImpl.java:37)
at com.google.firebase.database.connection.PersistentConnectionImpl$1$1.onSuccess(PersistentConnectionImpl.java:500)
at com.google.firebase.database.core.Context$1$1.onSuccess(Context.java:67)
at com.google.firebase.database.core.JvmAuthTokenProvider.getToken(JvmAuthTokenProvider.java:66)
at com.google.firebase.database.core.Context$1.getToken(Context.java:62)
at com.google.firebase.database.connection.PersistentConnectionImpl$1.run(PersistentConnectionImpl.java:490)
at com.google.firebase.database.connection.util.RetryHelper$1.run(RetryHelper.java:93)
at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.access$201(ScheduledThreadPoolExecutor.java:180)
at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.run(ScheduledThreadPoolExecutor.java:293)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at com.google.appengine.tools.development.BackgroundThreadFactory$1$1.run(BackgroundThreadFactory.java:60)
I don’t get the same errors when running in Google App Engine. I have noticed that this only occurs when I use firebase-admin 5.6.0 or greater. I do not get this error with version 5.5.0
Any ideas what I should do to resolve this please?
Start the app in a local environment (Android Studio)
DatabaseReference ref = FirebaseDatabase.getInstance().getReference();
//N.B. It's the call to getReference() that creates the error, not getInstance()
I tried to use the firebase-admin-java to authenticate my user via Google.
Every time I was getting this error:
com.google.firebase.auth.FirebaseAuthException: Error while verifying token signature.
The problem was the proxy. So I tried to set the proxy options like this:
InputStream serviceAccount = getClass().getClassLoader().getResourceAsStream(<fileName>);
Proxy proxy = new Proxy(Proxy.Type.HTTP, new InetSocketAddress(<address>, <port>));
HttpTransport httpTransport = new NetHttpTransport.Builder().setProxy(proxy).build();
HttpTransportFactory httpTransportFactory = () -> httpTransport;
FirebaseOptions options = new FirebaseOptions.Builder()
.setCredentials(GoogleCredentials.fromStream(serviceAccount, httpTransportFactory))
.setDatabaseUrl(<adress>)
.setHttpTransport(httpTransport)
.build();
FirebaseApp.initializeApp(options);
FirebaseToken decodedToken = FirebaseAuth.getInstance().verifyIdTokenAsync(<token>).get();
But I was still getting the same error.
A work around that works is to define the proxy parameters as system properties:
System.setProperty("http.proxyHost", <address>);
System.setProperty("http.proxyPort", <port>);
System.setProperty("https.proxyHost", <address>);
System.setProperty("https.proxyPort", <port>);
It seems like the problem comes from this line in the code:
FirebaseTokenVerifier - line 52
public static final GooglePublicKeysManager DEFAULT_KEY_MANAGER =
new GooglePublicKeysManager.Builder(new NetHttpTransport.Builder().build(), new GsonFactory())
.setClock(Clock.SYSTEM)
.setPublicCertsEncodedUrl(CLIENT_CERT_URL)
.build();
The default GooglePublicKeysManager doesn't take the custom transport given in the FirebaseOptions.
I opened a PR #151 with a fix for this issue.
If a user first connects social media accounts (e.g., Facebook, Twitter) and then a UpdateRequest.setPassword() is applied using the Java SDK, the connections to social media are wiped out and must be linked again. Should that be? I don't think an update of a password should remove those connections.
My web app runs on Google App Engine. I initialise the App:
try {
FirebaseApp.initializeApp(options);
}
catch(Exception error){
Log.info("FirebaseApp already initialised");
return;
}
and get a reference to the database:
DatabaseReference ref = FirebaseDatabase.getInstance().getReference();
Log.info("Database ref obtained.");
I then listen for children in the database:
ref.addChildEventListener(new ChildEventListener() {
@Override
public void onChildAdded(DataSnapshot dataSnapshot, String s) {
Log.info("Child Added");
//Do stuff here
}
});
I already have an entry in the database. On starting my webapp using version 5.11.0 the child event listener fires immediately. On repeating this using version 6.0.0 or 6.1.0 the event listener never fires.
Is there something special about GAE and version 6.0.0?
This API is currently only available for the Admin Node.js SDK.
It would be great having it here as well. Is it somehow on the roadmap?
Task<Void> task = mDatabase.setValue(item);
Even after task is completed (I'm firing an OnCompleteListener), the current thread is kept always alive.
Exact same error in grpc/grpc-java#4025 started to occur suddenly and keep occurs in both our server environment and local development environment.
As dependency goes firebase-admin-java:5.9.0
> google-cloud-core-grpc:1.15.0
and google-cloud-firestore:0.33.0-beta
> grpc-netty:1.9.0
> netty-codec-http2:4.1.17.Final
(checked with dependencyDot
command in sbt-updates)
I resolved this error by adding dependency "io.netty" % "netty-codec-http2" % "4.1.22.Final"
, so I think there should be dependency upgrades to upgrade netty in dependency tree.
What happened? How can we make the problem occur?
This could be a description, log/console output, etc.
It just started to occur suddenly and is occurring continuously until upgrade netty-codec-http2. grpc-java project seems to fail to find a way to reproduce the error.
// TODO(you): code here to reproduce the problem
Several users have reported issues with our use of this library (#112 being the latest). A number of frameworks seem to be using various conflicting versions of this library, which causes errors when trying to use Admin SDK in those frameworks. To make matters worse, there's also another different artifact which has the exact same package structure! It is possible to overcome this type of errors by carefully analyzing the dependency tree, and removing any conflicting artifacts. But it still results in a poor first-time user experience. Therefore we should consider using another, less ambiguous JSON library like gson in Admin SDK.
This won't be easy, since a good part of our RTDB JSON support is tied to this library at the moment. Perhaps we can start migrating non-RTDB code first.
Is it possible to make the Firebase Admin SDK compatible with OSGI ?
The minimal requirements would be to add OSGI metadata to the manifest.
To go further, you could rely on the OSGI service model, here is a project example :
https://github.com/cdecode/org.cdecode.firebase
In this project the API was redefined to not expose internal classes to consumers, the implementation is based on the version 5.2.0 of firebase and can be configured in an OSGI way.
The avantage of this will be firstly to support a new runtime environment, and secondly, if you go further, to minimize the impact on the consumer bundles.
Inside CustomClassMapper
in method deserializeToClass(Object obj, Class<T> clazz)
, the conditional statement wrongly assumes the value is of primitive type if Number.class.isAssignableFrom(clazz)
.
BigDecimal returns true but is not primitive, and throws an IllegalArgumentException
in deserializeToPrimitive(Object obj, Class<T> clazz)
There are several issues in the Admin SDK with respect to how it creates and uses threads:
Task
instances. This tends to make implementing simple use cases unnecessarily complex (e.g. creating a custom token and sending back as a servlet response).ThreadFactory
is initialized statically, and not configurable.Tasks
API is visible to user code. A user can kick off arbitrary background tasks using this API, which will get executed on the main thread pool of the SDK, un-regulated.In order to address these limitations, we can consider the following changes:
FirebaseAuth
).BlockingFirebaseAuth auth = FirebaseAuth.getBlockingInstance();
String customToken = auth.createCustomToken("user1");
Tasks
API. We can consider using the ApiFutures
from Google Cloud Commons (this is similar to Guava's ListenableFutures
) as a replacement.FirebaseAuth auth = FirebaseAuth.getInstance();
ApiFuture<String> customTokenFuture = auth.createCustomToken("user1");
// The following should not be supported
// Tasks.call(new Callable(){...});
Currently the Admin SDK depends on the google-api-client
library for all credential processing. But GCP at large is moving towards the new https://github.com/google/google-auth-library-java library. This library has better, cleaner APIs for parsing credential files, and integrates well with other gcloud SDKs. We should migrate the Admin SDK to use this new library.
This dependency is still at v0.6 and the API is subject to change. It might be a good idea to wait until they release v1.0.
We have the following exclusion rule set for the maven-source-plugin:
<excludes>
<exclude>com/**</exclude>
</excludes>
This is a left over from our pre-open source days. We should get rid of it now.
Hi,
We are using Firebase Admin to send messages from AppEngine. All works fine most of the time... however every now and then all Firebase calls start timing out (we wait for 20 seconds max). The calls are being made on a B2 class (configured for max 2 instances) which is fed data via task queue. During normal operation each call takes about 100-150ms. If we kill the instance everything starts working OK until next time. This was tested on 5.5.0 and also 5.4.0. Most of the calls are updateChildrenAsync(). What's also weird is that timeouts happen only on one of the two database shards (we are sharding databases within a single project) we use.
We can reproduce the problem by submitting 1000 jobs (in the end one job calls one updateChildrenAsync() (each job starts an operation and waits for it to complete). So under load it start to timeout.
Because of that we increased max instances to 5 and changed the class to B4... seems to work fine now.
I cannot explain to myself why this is happening... Even with limited resources there should be no timeouts ... AppEngine should limit the rate at which the task queue is being processed - it won't flood one instance over its limits.
So, if someone could explain why this is happening (is Firebase's thread model messing up AppEngine in a negative way?) Is it just that Firebase needs stronger instances? Are there any special considerations when running Firebase on AppEngine? Are there any risks of leaking resources (e.g. threads)?
I apologize because I can't describe the problem in more detail. Any hints on the matter are appreciated.
I'm trying to create a user through the Authentication API. However, I'm always receiving an ExecutionException with the message:
com.google.firebase.auth.FirebaseAuthException: IO error while creating user account
I do not fully understand the message. However, I have tried all the following:
Below are the relevant pieces of code:
A) Initializing the FirebaseApp:
public class FirebaseService {
private static final String projectId = "HIDDEN"; //hidden for reporting issue only
static {
try {
// InputStream is = new FileInputStream(
// new File("WEB-INF/service-account-credentials.json"));
FirebaseOptions options = new FirebaseOptions.Builder()
.setCredentials(GoogleCredentials.getApplicationDefault())
//.setDatabaseUrl("https://"+projectId+".firebaseio.com")
.setProjectId(projectId)
.build();
FirebaseApp.initializeApp(options);
} catch (Exception e) {
SimpleLogger.log(Level.SEVERE, e.toString(), e);
}
}
...
B) Creating the user: (in a method)
CreateRequest request = new CreateRequest()
.setEmail(manager.email) //tried different emails. Valid format
//.setEmailVerified(false) //tried with and without, and true/false
// .setPassword("LsjaA76as%Asd"); //for testing purposes, tried with and without
.setPhoneNumber(manager.phone) //valid format. Tried without as well
.setDisplayName(manager.name) //English letters only
//.setPhotoUrl("http://www.example.com/12345678/photo.png") //tried with and without
.setDisabled(!manager.active); //tried with and without
try {
UserRecord userRecord = FirebaseAuth.getInstance().createUserAsync(request).get();
return userRecord.getUid();
} catch (InterruptedException | ExecutionException e) {
throw new ServiceUnavailableException("Could not create user: " + e.getMessage());
}
Note:
The verify token does work:
FirebaseAuth.getInstance().verifyIdTokenAsync(token).get();
Am I doing something wrong?
It would be useful to have a shaded jar with packaged dependencies and relocated to another package to prevent version conflicts (specially because of other dependencies which require a different version of netty).
Admin Java SDK uses a default JsonFactory
and a default HttpTransport
everywhere. But users should be allowed to configure these where appropriate. For instance, when the SDK is deployed behind a proxy, it becomes unable to make any HTTP requests, since the default HttpTransport
is setup without proxy support. If this was configurable, users can init a transport with proxy support and pass it in.
I believe this needs to happen in 2 places:
JsonFactory
and HttpTransport
arguments. These methods already exist, but are package-protected.JsonFactory
and HttpTransport
via FirebaseOptions
. These can be plumbed into everywhere else in the SDK.It is possible to have the credentials also take the parameters from FirebaseOptions
, but that's going to be a breaking change, and we probably can live without it.
I am using this admin sdk version 5.5.0 with the new firestore. I was making batch writes and noticing that larger ones (1000 documents) were not working. The listener of the apifuture gets called, but the objects are just not in my store. With smaller batches (500 documents) it seems to work. I tried to find a maximum batch size or timeout in the documentation but with no success.
According to docs, for now setting custom claims is available only for JS.
Would be nice to have this option also in Java
The CI server adds product flavors to our Android app. When a flavor is added, the project must be sync'ed
using the Firebase plugin in Android Studio, so that the new flavor is added to the Firebase project and the new "google-services.json" file is downloaded to the project.
We would like to be able to do that without Android Studio. If it was added to this project, one could create a custom Gradle plugin or create a command line tool for the task and execute that from the CI server.
Admin Java SDK sometimes becomes unresponsive after operating without problems for several days. Issue is random and intermittent. There are no specific error messages or stack traces dumped when this happens.
After analyzing the App Engine logs for a user application that encounters this issue regularly, we have identified the following issue which is a strong candidate for the root cause (a 100% certain diagnosis is not possible due to the lack of error traces).
When the SDK encounters a connection issue (due to a backend server restart, or some other networking issue), which lasts longer than 2-3 seconds, the SDK starts running reconnect attempts aggressively. Each attempt instantiates 2 Threads (socket reader and writer). If the reader terminates with an error, which is the case with an extended connectivity issue, the writer thread will never even start. However, such leaked threads count towards the thread quota (10) of Google App Engine. After a number of reconnect attempts the SDK will get into a state where it can no longer launch new threads, and therefore cannot re-establish the connection with Firebase.
Another related cause could be the rate at which the SDK runs reconnect attempts. This is supposed to be a variant of exponential backoff, but due to a high jitter (probabilistic) factor, SDK ends up running a large number of reconnect attempts in a short span of time. Thread creation and termination are expensive operations in GAE, and it might make sense to lower the jitter factor so that exponential backoff takes effect.
Add a source map to the doc generation process so that reference docs can link directly into source files for each function/constant/etc.
Please provide an API for setting the mutable_content
property for iOS in Firebase Notifications.
com.google.firebase.messaging.Aps
class exposes some some properties like content-available
but not mutable_content
.
mutable_content
property is important for processing notifications in an UNNotificationServiceExtension
.
Here is my code
FileInputStream serviceAccount = new FileInputStream("firebase.json");
FirebaseOptions options = new FirebaseOptions.Builder()
.setCredential(FirebaseCredentials.fromCertificate(serviceAccount))
.setDatabaseUrl("https://xxxxx.firebaseio.com/")
.build();
FirebaseApp.initializeApp(options);
FirebaseAuth.getInstance();
FirebaseAuth.getInstance();
causing the issue. The error log stack is here
Exception in thread "main" java.lang.NoSuchMethodError: com.google.common.base.Preconditions.checkState(ZLjava/lang/String;Ljava/lang/Object;)V
at com.google.firebase.FirebaseApp.checkNotDeleted(FirebaseApp.java:314)
at com.google.firebase.FirebaseApp.getOptions(FirebaseApp.java:260)
at com.google.firebase.auth.FirebaseAuth.<init>(FirebaseAuth.java:74)
at com.google.firebase.auth.FirebaseAuth.<init>(FirebaseAuth.java:61)
at com.google.firebase.auth.FirebaseAuth.<init>(FirebaseAuth.java:52)
at com.google.firebase.auth.FirebaseAuth$FirebaseAuthService.<init>(FirebaseAuth.java:316)
at com.google.firebase.auth.FirebaseAuth.getInstance(FirebaseAuth.java:98)
at com.google.firebase.auth.FirebaseAuth.getInstance(FirebaseAuth.java:85)
at com.datasignstech.lam.core.google.GoogleInterface.main(GoogleInterface.java:119)
I am not sure why I am getting the above error. I see the code and at FirebaseApp.java:314 it is passing 3 arguments, but in error it is showing only two arguments, which is not there in Preconditions. Kindly help me in this.
I am using firebase-admin sdk: 5.2.0
Jdk: 1.8.0
OS: Ubuntu 16.04
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.