111
102

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

[Firestore] Google認証で特定のドメインのユーザーだけアクセスを許可する

Posted at

Firebase AuthenticationでGoogleアカウントによるログインを実装するのは簡単ですが、デフォルトだと全てのGoogleアカウントでログインできるようになっています。

社内向けのアプリケーションなどでは、特定のドメインのユーザーのみアクセスを許可したいケースがあると思いますが、そのようなケースの実装方法が案外出回っていなかったので、まとめておきます。

検証環境

  • Angular6
  • @angular/fire: v5.0.2
  • firebase: v5.4.1

今回はAngularを例にしていますが、他のフレームワークでも大きな違いはないと思います。

AngularFire

AngularでFirebaseを使うには、AngularFireという公式のライブラリを使うのが一番早いです。
AngularFireのセットアップとAuthenticationの基本的な実装方法は以下を参照。

フロントエンドでの制御

例として、AuthServiceというclassに googleLogin() というメソッドを実装しました。
GoogleAuthProviderをnewした後、setCustomParameters()hd というパラメータにドメインを指定することで、Googleログインのポップアップで、指定したドメインのメールアドレスしか入力できないようになります。

auth.service.ts
import { Injectable } from '@angular/core';
import { auth } from 'firebase/app';
import { AngularFireAuth } from '@angular/fire/auth';
import { AngularFirestore, AngularFirestoreDocument } from '@angular/fire/firestore';

@Injectable({
  providedIn: 'root'
})
export class AuthService {

  constructor(
    private afAuth: AngularFireAuth,
    private afStore: AngularFirestore
  ) {}

  googleLogin() {
    const provider = new auth.GoogleAuthProvider();
    provider.setCustomParameters({
      hd: 'yourdomain.com'
    });

    return this.afAuth.auth.signInWithPopup(provider)
      .then(credential => {
        // Update user document in Firestore (おまけ)
        this.updateUser(credential.user);
      });
  }

  private updateUser(user: firebase.User) {
    const userRef: AngularFirestoreDocument<any> = this.afStore.doc(`users/${user.uid}`);

    const data = {
      uid: user.uid,
      email: user.email,
      displayName: user.displayName,
      photoURL: user.photoURL
    };

    return userRef.set(data, { merge: true });
  }
}

googleLogin() がコールされると、以下のようなポップアップが表示されます。

ちなみに、ログイン情報はブラウザのIndexedDBに保存されます。

サーバーサイド(Firestore)での制御

フロントエンドでの制御だけだと完璧ではないので、サーバーサイド(Firestore)でも、特定のドメインのユーザーしかアクセスできないように設定します。

Firestore Security Rules

Firestoreのセキュリティルールで、特定のドメインのユーザーしかドキュメントにアクセスできないようにします。
firebase init でFirestoreを使うように設定しているプロジェクトだと、プロジェクトのディレクトリ直下に firebase.jsonfirestore.rules があると思います。

firestore.rules に以下のルールを追加することで、yourdomain.com ドメインのユーザー以外は全てのドキュメントにアクセスできないようになります。

firestore.rules
service cloud.firestore {
  match /databases/{database}/documents {
    match /{document=**} {
      allow read, write: if isValidUser();
    }
  }

  function isValidUser() {
    return request.auth.uid != null && request.auth.token.email.matches('.*@yourdomain.com');
  }
}

シミュレータでテスト

設定したルールが意図した動きをするかどうか、Firebase Consoleのシミュレータでテストできるので、ルールをデプロイする前に一度テストすることをオススメします。

image.png

ルールをデプロイ

$ firebase deploy --only firestore:rules

参考記事

111
102
1

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
111
102

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?