Как проверить токен Firebase в конечных точках Google? - PullRequest
0 голосов
/ 11 января 2019

Я ознакомился с документацией по аутентификации в firebase, а также с учебником по этому вопросу. Предполагая, что токен будет поступать в клиент из заголовка, я создал собственный класс аутентификатора и получаю сообщение об ошибке для задачи «The type TaskQueuePb.TaskQueueQueryAndOwnTasksResponse.Task is not generic; it cannot be parameterized with arguments <FirebaseToken>». Тем не менее, я не вижу другого импорта, и учебник, кажется, не объясняет больше об этом.

Пожалуйста, используйте код ниже:

package com.travelplannr.endpoint.firebase;

import java.io.File;
import java.io.FileInputStream;
import java.io.InputStream;
import java.util.concurrent.ExecutionException;
import java.util.logging.Level;
import java.util.logging.Logger;

import javax.servlet.http.HttpServletRequest;

import com.google.api.server.spi.ServiceException;
import com.google.api.server.spi.auth.common.User;
import com.google.api.server.spi.config.Authenticator;
import com.google.appengine.api.taskqueue.TaskQueuePb.TaskQueueQueryAndOwnTasksResponse.Task;
import com.google.auth.oauth2.GoogleCredentials;
import com.google.firebase.FirebaseApp;
import com.google.firebase.FirebaseOptions;
import com.google.firebase.auth.FirebaseAuth;
import com.google.firebase.auth.FirebaseToken;

public class CustomAuthenticator implements Authenticator {

     private static final Logger logger = Logger.getLogger(CustomAuthenticator.class.getName());

        static {
            try {
                FileInputStream serviceAccount = new FileInputStream("path/to/serviceAccountKey.json");

                FirebaseOptions options = new FirebaseOptions.Builder()
                    .setCredentials(GoogleCredentials.fromStream(serviceAccount))
                    .setDatabaseUrl("https://<DATABASE_NAME>.firebaseio.com/")
                    .build();

                FirebaseApp.initializeApp(options);

            } catch (Exception e) {
                logger.log(Level.SEVERE, e.toString(), e);
            }
        }

        @Override
        public User authenticate(HttpServletRequest httpServletRequest) {

            //get token
            final String authorizationHeader = httpServletRequest.getHeader("Authorization");

            //verify
            if(authorizationHeader != null) {
                Task<FirebaseToken> task = FirebaseAuth.getInstance().verifyIdToken(authorizationHeader.replace("Bearer ", ""));

                //wait for the task
                try {
                    Tasks.await(task);
                } catch (ExecutionException e) {
                } catch (InterruptedException e) {
                }

                FirebaseToken firebaseToken = task.getResult();
                User user = new User(firebaseToken.getUid(), firebaseToken.getEmail());
                return user;
            }
        return null;
    }
}

Пожалуйста, помогите! Заранее спасибо.

1 Ответ

0 голосов
/ 18 января 2019

Я думаю, что здесь есть две разные проблемы в одной строке кода. Во-первых, кажется, что в вашем назначении есть несоответствие левого типа получения из возвращаемого типа. Из того, что я вижу по ссылке API Java FirebaseAuth , сигнатура метода:

FirebaseToken verifyIdToken(String token)

Итак, verifyIdToken возвращает FirebaseToken, но вы пытаетесь присвоить его Task<FirebaseToken>, который является другим несовместимым типом. Во-вторых, Task<FirebaseToken> также является недопустимым типом, который следует использовать, поскольку этот класс Task не является универсальным, поэтому его вообще нельзя параметризировать. Это ошибка, которую вы видите от компилятора, но эта деталь становится неактуальной, если вы вообще отказываетесь от использования Task, потому что это не нужно:

FirebaseToken firebaseToken = FirebaseAuth.getInstance().verifyIdToken(authorizationHeader.replace("Bearer ", ""));

Просто удалите весь ваш другой код, пытаясь использовать Task и Tasks.await().

Похоже, вы могли смешивать и сопоставлять синхронные и асинхронные источники информации о том, как сделать этот вызов. Поскольку код, который вы написали, собирался немедленно дождаться выполнения асинхронной задачи, вам, вероятно, следует просто придерживаться синхронной версии API (verifyIdToken()) вместо того, чтобы пытаться использовать асинхронный вариант (verifyIdTokenAsync() ), что могло привести к некоторой путанице при попытке следовать примерам.

...