Casual Developers Note

エンジニアやデザイナー向けの技術情報・英語学習情報・海外留学情報・海外旅行情報を提供中。世界を旅して人生を楽しもう。

  • ホーム
  • 技術 Tips & Tutorials
  • 技術塾
  • ライフハック
  • 海外留学
  • 英語学習
  • コラム
  • お問い合わせ
現在の場所:ホーム / アーカイブlogin

2018年4月6日 By KD コメントを書く

FacebookログインをExpressとPassportでサクッと実装する方法

FacebookログインをExpressとPassportでサクッと実装する方法

ソーシャルログインの実装はスタートアップ起業にとっては無くてはならないログイン実装の代替となっています。今回はFacebookログインのAPIを、NodeJSでの一般的な実装方法である、ExpressとPassportを使った実装方法をご紹介します。

はじめに

以前の記事でFacebookログインを確認する簡単なAPIを作りました。簡単なテストとしてはそれで十分なのですが、今回はもう一歩踏み込んで、ExpressとPassportを使って、実際に使えるAPIをサクッと実装する方法をご紹介します。

FacebookログインのJavascriptのSDKをサクッと試す方法

Facebookログインを実装しよう

前提

以下がインストールされている前提で進めます。

  • NodeJS
  • Yarn
  • Docker
  • Robo 3T (任意)

細かいバージョンは「環境」を参照して下さい。

Facebook For Developersでアプリの登録

以前作成した「sample app」を使います。

今回はローカルホストで実行できるように以下の設定をします。

  • アプリドメイン : localhost

13b47f02b0afa6772e34246ac9dd946c

リダイレクト先のURLを設定します。

  • 有効なOAuthリダイレクトURL : http://localhost:3000/auth/facebook/callback

スクリーンショット 2018 02 25 23 42 43

環境の作成

今回用のフォルダとファイルを作って、必要なパッケージをインストールします。

$ mkdir facebook-project
$ cd facebook-project
$ yarn init -y
$ yarn add express cookie-session mongoose passport passport-facebook 
$ mkdir models
$ touch models/user.js
$ touch server.js

MongoDBをDockerイメージで作成

ローカルにMongoDBがインストールされている人はそれでも良いですが、インストールしていない人はこのためだけに環境を構築するのは面倒だと思いますので、Dockerイメージを使いましょう。

$ docker container run -d --rm --name mongo-docker -p 27018:27017 mongo:3.6.2
$ docker container ls
CONTAINER ID        IMAGE               COMMAND                  CREATED                  STATUS              PORTS                      NAMES
447858ed0598        mongo:3.6.2         "docker-entrypoint.s…"   Less than a second ago   Up 15 seconds       0.0.0.0:27018->27017/tcp   mongo-docker
$ docker exec -it mongo-docker mongo --version
MongoDB shell version v3.6.2
git version: 489d177dbd0f0420a8ca04d39fd78d0a2c539420
OpenSSL version: OpenSSL 1.0.1t  3 May 2016
allocator: tcmalloc
modules: none
build environment:
    distmod: debian81
    distarch: x86_64
    target_arch: x86_64

「–rm」オプションを指定しているので、停止するとコンテナは削除されます。ゴミが残らないのでテストにはもってこいです。

「user.js」の実装

const mongoose = require('mongoose');
const { Schema } = mongoose;

const userSchema = new Schema({
  displayName: String,
  facebookId: String
});

const User = mongoose.model('users', userSchema);

module.exports = User;

「server.js」の実装

ソースコードは以下になります。

const express = require('express');
const mongoose = require('mongoose');
const cookieSession = require('cookie-session');
const passport = require('passport');

const PORT = process.env.PORT || 3000;
const FACEBOOK_APP_ID = '{your-app-id}';
const FACEBOOK_APP_SECRET = '{your-app-secret}';
const MONGO_URL = 'mongodb://localhost:27018/test-db';

const FacebookStrategy = require('passport-facebook').Strategy;
const User = require('./models/user');

passport.serializeUser((user, done) => {
  done(null, user.id);
});

passport.deserializeUser((id, done) => {
  User.findById(id).then(user => {
    done(null, user);
  });
});

passport.use(
  new FacebookStrategy(
    {
      clientID: FACEBOOK_APP_ID,
      clientSecret: FACEBOOK_APP_SECRET,
      callbackURL: '/auth/facebook/callback'
    },
    (accessToken, refreshToken, profile, done) => {
      if (!profile) {
        return done(null, false);
      }

      User.findOne({ facebookId: profile.id })
        .then(existingUser => {
          if (existingUser) {
            done(null, existingUser);
          } else {
            new User({
              displayName: profile.displayName,
              facebookId: profile.id
            })
              .save()
              .then(user => done(null, user));
          }
        })
        .catch(err => done(err, null));
    }
  )
);

mongoose.connect(MONGO_URL);

const app = express();

app.use(
  cookieSession({
    maxAge: 30 * 24 * 60 * 60 * 1000,
    keys: ['facebook-auth']
  })
);
app.use(passport.initialize());
app.use(passport.session());

app.get(
  '/auth/facebook',
  passport.authenticate('facebook', {
    scope: ['public_profile']
  })
);

app.get(
  '/auth/facebook/callback',
  passport.authenticate('facebook'),
  (req, res) => {
    res.send({ message: 'The user is logging in' });
  }
);

app.get('/api/logout', (req, res) => {
  req.logout();
  res.send({ message: 'The user logged out' });
});

app.get('/api/user', (req, res) => {
  res.send(req.user);
});

app.listen(PORT, () => {
  console.log(`Server is starting on ${PORT}...`);
});

「{your-app-id}」と「{your-app-secret}」には自分のIDとシークレットの値を入れて下さい。データベースのURLは「mongodb://localhost:27018/test-db」にしています。Dockerコンテナ作成時に設定したポート27018ですね。

リソースのアクセス許可の範囲

Facebookのリソースにはアクセス許可の権限が細かく決められています。その設定は「passport.authenticate」の「scope」で行っています。

今回はデフォルトである「public_profile」を設定しています。利用者の公開プロフィールの一部のアイテムを取得できます。

詳しいアクセス許可に関しては公式サイトを確認して下さい。

動作確認

サーバーの起動

それでは、作成した「server.js」を起動しましょう。

$ node server.js
Server is starting on 3000...

ログインの確認

ブラウザを開き、「http://localhost:3000/auth/facebook」にアクセスしましょう。

スクリーンショット 2018 02 26 0 06 58

ログインできました!

データベースの値の確認

次に、Robo 3TからMongoDBに接続します。

スクリーンショット 2018 02 26 0 04 13

スクリーンショット 2018 02 26 0 04 33

「test-db」にユーザ情報が登録されています。

スクリーンショット 2018 02 26 0 09 03

ユーザ情報の取得

「http://localhost:3000/api/user」にアクセスしてみましょう。

スクリーンショット 2018 02 26 0 24 57

データベースに登録されていたユーザ情報と同じ情報が表示されています。

ログアウトの確認

最後に、「http://localhost:3000/api/logout」にアクセスしてみましょう。

スクリーンショット 2018 02 26 0 25 22

ログアウトされました!「http://localhost:3000/api/user」にアクセスしてもユーザ情報は取得できません。

最後に

いかがでしたか?FacebookログインのAPIはPassportを使うことでいとも簡単に実装できます。まさにサクッとです。この簡単なログイン実装を使わない手はありません。何かサービスを作る時にソーシャルログインとして導入してみてはいかがですか?

環境

  • PC : macOS High Sierra 10.13.3
  • Robo 3T : 1.1.1
  • NodeJS : v9.5.0
  • Yarn : 1.3.2
  • express : 4.16.2,
  • cookie-session : 2.0.0-beta.3,
  • mongoose : 5.0.7
  • passport : 0.4.0
  • passport-facebook : 2.1.1
  • Docker : 17.12.0-ce
  • MongoのDockerイメージ : 3.6.2

カテゴリ : 技術 Tips & Tutorials タグ : auth, facebook, login, nodejs

ブログ更新情報や海外の関連情報などを配信する無料メルマガ

Sponsored Links

About Author

KD

世界を旅し日本を愛するエンジニア。大学でコンピュータサイエンスの楽しさを学び、日本の大手IT企業で働く中で、新しい技術やスケールするビジネスが北米にある事に気づく。世界に挑戦するための最大の壁が英語であったため、フィリピン留学およびカナダ留学を経て英語を上達させた。現在は日本在住でエンジニアとして働きつつ、次の挑戦に備えて世界の動向を注視している。挑戦に終わりはない。このブログでは、エンジニアやデザイナー向けの技術情報から、海外に留学したい人向けの留学情報、海外に興味がある人向けの海外旅行情報など、有益な情報を提供しています。

https://casualdevelopers.com/

最近の投稿

  • 2020年JS周辺のバックエンド寄りの注目技術!ネクストNodeJSの「Deno」と分散型パッケージレジストリの「Entropic」の紹介

    2020年JS周辺のバックエンド寄りの注目技術!ネクストNodeJSの「Deno」と分散型パッケージレジストリの「Entropic」の紹介

    2020年1月13日
  • 今さら聞けないJavaによる関数型プログラミング入門 ~ラムダ式、ストリーム、関数型インターフェース~

    今さら聞けないJavaによる関数型プログラミング入門 ~ラムダ式、ストリーム、関数型インターフェース~

    2019年11月4日
  • ReactのためのEslintおよびPrettierの設定方法 ~Airbnb JavaScript Style Guideの適用~

    ReactのためのEslintおよびPrettierの設定方法 ~Airbnb JavaScript Style Guideの適用~

    2019年10月30日
  • BashからZshに移行する方法(Mac編)

    BashからZshに移行する方法(Mac編)

    2019年10月21日
  • Create React Appを使わないでゼロからReactの開発環境を構築する方法(Webpack/Docker編)

    Create React Appを使わないでゼロからReactの開発環境を構築する方法(Webpack/Docker編)

    2019年9月30日

カテゴリ

  • 技術 Tips & Tutorials (100)
  • 技術塾 (6)
  • ライフハック (26)
  • 海外留学 (12)
  • 英語学習 (3)
  • コラム (6)

アーカイブ

最高の学習のために

人気記事ランキング

  • MySQLで「ERROR 2003 (HY000): Can't connect to MySQL server」と怒られた時の対処法
    MySQLで「ERROR 2003 (HY000): Can't connect to MySQL server」と怒られた時の対処法
  • Jupyter Notebookで「The kernel appears to have died. It will restart automatically.」というエラーが出た場合の原因と対処法
    Jupyter Notebookで「The kernel appears to have died. It will restart automatically.」というエラーが出た場合の原因と対処法
  • 爆速でJenkinsをマスターしよう(GitHubアカウント統合編) ~ JenkinsのGitHub Organizationの設定方法 ~
    爆速でJenkinsをマスターしよう(GitHubアカウント統合編) ~ JenkinsのGitHub Organizationの設定方法 ~
  • Expressで「Cannot set headers after they are sent to the client」と怒られた時の対処法
    Expressで「Cannot set headers after they are sent to the client」と怒られた時の対処法
  • SAKURAのメールボックスで独自ドメインのメールを設定し、Gmail経由で送受信する方法
    SAKURAのメールボックスで独自ドメインのメールを設定し、Gmail経由で送受信する方法
  • バンクーバー留学豆知識:バンクーバーのATMで日本の銀行のキャッシュカードを使ってお得にお金を引き出す方法
    バンクーバー留学豆知識:バンクーバーのATMで日本の銀行のキャッシュカードを使ってお得にお金を引き出す方法
  • [tips][perl] Perlで文字コードをいい感じに処理する方法
    [tips][perl] Perlで文字コードをいい感じに処理する方法
  • PythonでWebスクレイピング入門(Scrapy+Selenium編)
    PythonでWebスクレイピング入門(Scrapy+Selenium編)
  • Amazon EC2インスタンスにSSHできなくなった時の対処法
    Amazon EC2インスタンスにSSHできなくなった時の対処法
  • SpringBootのProfile毎にプロパティを使い分ける3つの方法
    SpringBootのProfile毎にプロパティを使い分ける3つの方法

Bitcoin寄付 / BTC Donation

Bitcoinを寄付しよう

BTC
Select Payment Method
Personal Info

Donation Total: BTC 0.0010

このブログの運営のためにBitcoinでの寄付を募集しています。お気持ち程度の寄付を頂けると管理者の励みになります。

Bitcoin寄付について知りたい方はこちらの記事へ

ビットコイン取引ならここ

  • ホーム
  • 技術 Tips & Tutorials
  • 技術塾
  • ライフハック
  • 海外留学
  • 英語学習
  • コラム
  • サイトマップ
  • タグ一覧
  • プライバシーポリシー
  • お問い合わせ

Copyright © 2023 KD - Casual Developers Notes