REST 요청 인증

Firebase SDK는 Firebase Realtime Database와 이루어지는 모든 인증과 통신을 사용자 대신 처리합니다. 그러나 클라이언트 SDK가 없는 환경이거나 영구 데이터베이스 연결에 따르는 오버헤드를 피하려는 경우 Realtime Database REST API를 사용하여 데이터를 읽고 쓸 수 있습니다.

다음 방법 중 하나를 통해 사용자를 인증합니다.

  1. Google OAuth2 액세스 토큰 - 일반적으로 Realtime Database에 대한 읽기 및 쓰기 가능 여부는 Realtime Database 규칙으로 관리됩니다. 그러나 서비스 계정에서 생성한 Google OAuth2 액세스 토큰을 사용하면 서버에서 데이터에 액세스하고 서버에 데이터에 대한 전체 읽기 및 쓰기 액세스 권한을 부여할 수 있습니다.

  2. Firebase ID 토큰 - 예를 들어 클라이언트 SDK의 Realtime Database 규칙을 통해 액세스를 제한하려는 경우 개별 사용자로 인증된 요청을 보낼 수도 있습니다. REST API는 클라이언트 SDK에서 사용하는 것과 동일한 Firebase ID 토큰을 취합니다.

Google OAuth2 액세스 토큰

Realtime Database 규칙에 따라 공개적으로 읽거나 쓸 수 있는 데이터는 REST API를 통해서도 인증 없이 읽고 쓸 수 있습니다. 그러나 서버에서 Realtime Database 규칙을 우회하려면 읽기 및 쓰기 요청을 인증해야 합니다. Google OAuth2를 통한 인증 방법은 다음과 같습니다.

  1. 액세스 토큰을 생성합니다.
  2. 액세스 토큰으로 인증합니다.

액세스 토큰 생성

Realtime Database REST API는 표준 Google OAuth2 액세스 토큰을 허용합니다. Realtime Database에 대한 적절한 권한이 있는 서비스 계정을 사용하여 액세스 토큰을 생성할 수 있습니다. 서비스 계정 키 파일이 없는 경우 Firebase Console의 서비스 계정 섹션 하단에 있는 새 비공개 키 생성 버튼을 클릭하면 새 서비스 계정 키 파일을 간편하게 생성할 수 있습니다.

서비스 계정 키 파일이 있으면 Google API 클라이언트 라이브러리 중 하나를 사용하여 다음과 같은 필수 범위를 갖는 Google OAuth2 액세스 토큰을 생성할 수 있습니다.

  • https://www.googleapis.com/auth/userinfo.email
  • https://www.googleapis.com/auth/firebase.database

다음은 다양한 언어로 Realtime Database REST API에 인증하는 Google OAuth2 액세스 토큰을 생성하는 방법을 보여주는 몇 가지 구현 예시입니다.

Node.js

Node.js용 Google API 클라이언트 라이브러리 사용:

var {google} = require("googleapis");

// Load the service account key JSON file.
var serviceAccount = require("path/to/serviceAccountKey.json");

// Define the required scopes.
var scopes = [
  "https://www.googleapis.com/auth/userinfo.email",
  "https://www.googleapis.com/auth/firebase.database"
];

// Authenticate a JWT client with the service account.
var jwtClient = new google.auth.JWT(
  serviceAccount.client_email,
  null,
  serviceAccount.private_key,
  scopes
);

// Use the JWT client to generate an access token.
jwtClient.authorize(function(error, tokens) {
  if (error) {
    console.log("Error making request to generate access token:", error);
  } else if (tokens.access_token === null) {
    console.log("Provided service account does not have permission to generate access tokens");
  } else {
    var accessToken = tokens.access_token;

    // See the "Using the access token" section below for information
    // on how to use the access token to send authenticated requests to
    // the Realtime Database REST API.
  }
});

자바

자바용 Google API 클라이언트 라이브러리 사용:

// Load the service account key JSON file
FileInputStream serviceAccount = new FileInputStream("path/to/serviceAccountKey.json");

// Authenticate a Google credential with the service account
GoogleCredential googleCred = GoogleCredential.fromStream(serviceAccount);

// Add the required scopes to the Google credential
GoogleCredential scoped = googleCred.createScoped(
    Arrays.asList(
      "https://www.googleapis.com/auth/firebase.database",
      "https://www.googleapis.com/auth/userinfo.email"
    )
);

// Use the Google credential to generate an access token
scoped.refreshToken();
String token = scoped.getAccessToken();

// See the "Using the access token" section below for information
// on how to use the access token to send authenticated requests to the
// Realtime Database REST API.

Python

google-auth 라이브러리 사용:

from google.oauth2 import service_account
from google.auth.transport.requests import AuthorizedSession

# Define the required scopes
scopes = [
  "https://www.googleapis.com/auth/userinfo.email",
  "https://www.googleapis.com/auth/firebase.database"
]

# Authenticate a credential with the service account
credentials = service_account.Credentials.from_service_account_file(
    "path/to/serviceAccountKey.json", scopes=scopes)

# Use the credentials object to authenticate a Requests session.
authed_session = AuthorizedSession(credentials)
response = authed_session.get(
    "https://<DATABASE_NAME>.firebaseio.com/users/ada/name.json")

# Or, use the token directly, as described in the "Authenticate with an
# access token" section below. (not recommended)
request = google.auth.transport.requests.Request()
credentials.refresh(request)
access_token = credentials.token

액세스 토큰으로 인증

인증된 요청을 Realtime Database REST API로 보내려면 위에서 생성한 Google OAuth2 액세스 토큰을 Authorization: Bearer <ACCESS_TOKEN> 헤더 또는 access_token=<ACCESS_TOKEN> 쿼리 문자열 파라미터로 전달합니다. 다음은 Ada의 이름을 읽는 curl 요청의 예시입니다.

curl "https://<DATABASE_NAME>.firebaseio.com/users/ada/name.json?access_token=<ACCESS_TOKEN>"

<DATABASE_NAME>Realtime Database의 이름으로 바꾸고 <ACCESS_TOKEN>을 Google OAuth2 액세스 토큰으로 바꾸세요.

요청이 성공하면 200 OK HTTP 상태 코드로 표시됩니다. 응답에는 검색 대상 데이터가 포함됩니다.

{"first":"Ada","last":"Lovelace"}

Firebase ID 토큰

사용자 또는 기기가 Firebase Authentication을 사용하여 로그인하면 Firebase는 ID 토큰을 고유하게 식별하는 ID 토큰을 만들고 Realtime DatabaseCloud Storage 등의 여러 리소스에 대한 액세스 권한을 부여합니다. ID 토큰을 다시 사용하여 Realtime Database REST API를 인증하고 사용자를 대신하여 요청할 수 있습니다.

ID 토큰 생성

클라이언트에서 Firebase ID 토큰을 검색하려면 클라이언트에서 ID 토큰 검색의 단계를 따릅니다.

ID 토큰은 짧은 시간 후에 만료되므로 검색한 후 최대한 빨리 사용해야 합니다.

ID 토큰으로 인증

인증된 요청을 Realtime Database REST API로 보내려면 위에서 생성한 ID 토큰을 auth=<ID_TOKEN> 쿼리 문자열 파라미터로 전달합니다. 다음은 Ada의 이름을 읽는 curl 요청의 예시입니다.

curl "https://<DATABASE_NAME>.firebaseio.com/users/ada/name.json?auth=<ID_TOKEN>"

<DATABASE_NAME>Realtime Database의 이름으로 바꾸고 <ID_TOKEN>을 Firebase ID 토큰으로 바꾸세요.

요청이 성공하면 200 OK HTTP 상태 코드로 표시됩니다. 응답에는 검색 대상 데이터가 포함됩니다.

{"first":"Ada","last":"Lovelace"}

이전 토큰

기존 Firebase 인증 토큰을 계속 사용하고 있다면 REST 인증을 위에서 설명한 인증 방법 중 하나로 업데이트하는 것이 좋습니다.

Realtime Database REST API는 보안 비밀을 포함하여 이전 인증 토큰을 통한 인증을 계속 지원합니다. Realtime Database 보안 비밀은 Firebase Console의 서비스 계정 섹션에서 확인할 수 있습니다.

보안 비밀은 장기 사용자 인증 정보입니다. 프로젝트에서 비밀 액세스 권한이 있는 사용자(예: 소유자)를 삭제할 때는 새 보안 비밀을 생성하고 기존 보안 비밀을 취소하는 것이 좋습니다.