Qiita Teams that are logged in
You are not logged in to any team

Log in to Qiita Team
Community
OrganizationAdvent CalendarQiitadon (β)
Service
Qiita JobsQiita ZineQiita Blog
78
Help us understand the problem. What is going on with this article?
@itagakishintaro

Node.js + Express + passport-twitterで認証Webアプリをつくる

More than 3 years have passed since last update.

Node.js+Express+MongoDBでWeb APIをつくるの続き的な感じで。

passportなどのインストール

passportは、Node.jsで使える認証用ミドルウェア。
http://passportjs.org/

package.json
{
    "name": "passport-twitter",
    "version": "0.0.1",
    "private": true,
    "dependencies":{
        "express": "*",
        "passport": "*",
        "passport-twitter": "*",
        "express-session": "*"
    }
}

package.jsonに追記したら、例のごとくインストール。

npm install

コードを書く

app.js

まずは、本体のapp.js。

// passport-twitter用
var session = require('express-session')
var auth = require('./passport');
var passport = auth.passport;

// passport-twitter用
app.use(passport.initialize()); 
app.use(passport.session()); 
app.use(session({secret: 'itagaki'}));

がpassport-twitter用の部分。
passport部分はrequire('./passport')で別のファイルに外出ししている。
また、ルーティング部分もrequire('./routes')で別ファイルに外出ししているので、routes.configRoutes(app, server, passport)でルーティング設定メソッドにpassportを渡しています。

app.js
'use strict';
var http = require('http');
var express = require('express');
// passport-twitter用
var session = require('express-session')
var auth = require('./passport');
var passport = auth.passport;
// ルーティングファイルを指定
var routes = require('./routes');
var app = express();
var server = http.createServer(app);

// passport-twitter用
app.use(passport.initialize()); 
app.use(passport.session()); 
app.use(session({secret: 'itagaki'}));
// 静的ファイルのルートディレクトリを指定
app.use(express.static(__dirname + '/public'));
// ルーティングを設定
routes.configRoutes(app, server, passport);
// リッスン
server.listen(3000);
console.log('Listening on port %d in %s mode', server.address().port, app.settings.env);

passport.js

passport.jsという名前は別に決まりでも何でもないので、注意。
KEYとSECRETは
https://apps.twitter.com/
で取得する。

基本は
http://passportjs.org/guide/twitter/
のコードのとおりなんだけど、Session部分は少し理解しにくい。
バージョンによっても少し書き方が違うみたいで、インターネットで情報を探してそのまま書いても動かないことがある。
結局は最新の公式サイトをみるのが一番早いかも。
http://passportjs.org/guide/configure/

passport.js
// http://passportjs.org/guide/twitter/
var TWITTER_CONSUMER_KEY = 'TWITTER_CONSUMER_KEY';
var TWITTER_CONSUMER_SECRET = 'TWITTER_CONSUMER_SECRET';
var passport = require('passport')
  , TwitterStrategy = require('passport-twitter').Strategy;

// Sessionの設定
// http://passportjs.org/guide/configure/
passport.serializeUser(function(user, done) {
    done(null, user.id);
});
passport.deserializeUser(function(obj, done) {
    done(null, obj);
});

passport.use(new TwitterStrategy({
    consumerKey: TWITTER_CONSUMER_KEY,
    consumerSecret: TWITTER_CONSUMER_SECRET,
    callbackURL: "http://localhost:3000/auth/twitter/callback"
  },
  function(token, tokenSecret, profile, done) {
    passport.session.id = profile.id;

    // tokenとtoken_secretをセット
    profile.twitter_token = token;
    profile.twitter_token_secret = tokenSecret;

    process.nextTick(function () {
        return done(null, profile);
    });
  }
));

module.exports = {passport: passport};

routes.js

例えば、secret/secret.htmlに認証をかけたいならこんな感じ。
先ほどのpassport.jsでdone(null, user.id);としたので、passport.session.idという感じでSessionからidを取得できる。
この場合は、Sessionにidがあれば、secret.htmlを表示するようにしている。
ちなみにfs.readFileは単にファイルを読み込んでいるだけ。

routes.js
'use strict';
var configRoutes;
var fs = require('fs');

configRoutes = function(app, server, passport) {
    app.get('/secret', function(request, response) {
        // 認証保護
        if(passport.session && passport.session.id){
            fs.readFile('./secret/secret.html', 'utf8', function (error, html) {
                response.send(html);
            });
        } else {
            response.redirect('/login');
        }   
    });

    // passport-twitter ----->
    // http://passportjs.org/guide/twitter/
    app.get('/auth/twitter', passport.authenticate('twitter'));
    app.get('/auth/twitter/callback', 
        passport.authenticate('twitter', { successRedirect: '/secret',
                                                failureRedirect: '/login' }));
    // <-----
}

module.exports = {configRoutes: configRoutes};

コード全体

Node.js+Express+MongoDBでWeb APIをつくるの続きなので、passport-twitterと関係ない部分があるので、少しわかりにくいかもしれませんが。。。

78
Help us understand the problem. What is going on with this article?
Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away

Comments

No comments
Sign up for free and join this conversation.
Sign Up
If you already have a Qiita account Login
78
Help us understand the problem. What is going on with this article?