Next.jsで簡易的なアクセス制限機能を実装するときに、アクセス接続元情報を参照する必要があった。
簡易的なアクセス制限機能であるため、クライアントを識別するには次の情報さえあれば良い。
(厳密にやるならばネットワーク上にサーバ等構築する必要はある。)
- IPアドレス
- User Agent
- ホスト名
これらの接続元情報をNext.jsで構築したアプリケーションで取得する方法について書く。
環境
- Next.js 12.0.4
実装
SSR(サーバーサイド)で実行されるgetServerSideProps
メソッドには、context
というオブジェクトが渡ってくる。
context
オブジェクトには、req
というリクエストオブジェクトが内包されており、リクエストヘッダーの情報も含んでいるため、前述した接続元情報はreq
オブジェクトから参照する。
getServerSideProps
からreq
を参照するには次のように記載する。
export const getServerSideProps: GetServerSideProps = async(context) => {
const { req } = context;
return {
props: {}
}
}
IPアドレスの取得
x-forwarded-for
ヘッダーからIPアドレスを参照する。
X-Forwarded-For - HTTP | MDN
x-forwarded-for
ヘッダーは、次のようにカンマ区切りの構造となっている。
X-Forwarded-For: <client>, <proxy1>, <proxy2>
proxyには、複数のプロキシを経由された場合に経由されたプロキシのIPアドレスが出力される。
接続元(client)のIPアドレスを取得するには、カンマ区切りしたリストの先頭を参照すれば良い。
const ipAddress = req.headers["x-forwarded-for"]
? String(req.headers["x-forwarded-for"]).split(',')[0]
: req.connection.remoteAddress
? req.connection.remoteAddress
: "";
User Agentの取得
User-Agent
ヘッダーからUser Agentを参照する。
User-Agent - HTTP | MDN
const userAgent = req.headers["user-agent"];
ホスト名の取得
ホスト名はHTTPヘッダーには含まれないため、IPアドレスから逆引きして取得する。
Node.jsのdns.lookupService
メソッドを使用してDNSサーバに問い合わせを行う。
import {lookupService} from "dns";
const getHostName = (ipAddress: string): Promise<string> => {
return new Promise(function(resolve, reject) {
lookupService(ipAddress, 22, function (error, hostname, service) {
if (error) {
return reject(error);
}
resolve(hostname);
});
});
};
const hostName = await getHostName(ipAddress);
dns.lookupService
メソッドは、問い合わせ成功時にコールバック関数を介してホスト名を返却する。
任意の変数などに初期化するには、Promiseオブジェクトでラップして返却させる。