はじめに.
以前、MCPサーバー側で認証処理を実装しましたが、今回はクライアント側の認証を実装しています。
OAuthで認証
MCPの認証のページに記述されているシーケンスを大雑把に振り返ってみます。
認証画面自体は、ブラウザやWebView的なもので表示することになるのですが、だがしかし、ブラウザ自体をそんなに信用して良いものなのでしょうか?
PKCE
という事で、先ほどのシーケンスにも記述していますが、PKCEの出番です。
ブラウザに認証画面の表示をお願いするときに、code_challengerと言われるハッシュ値を一緒に渡す。
そして、認証を実施、リダイレクトを利用してauthorization codeを取得。
code_challengerを生成する元となった、code_verifierと共にauthorization codeを認証サーバーに渡すことで、アクセストークンを得る。
これによって、ブラウザが悪さしたとしても、アクセストークンが盗まれないといった仕組みです。
code_verifierとcode_challengerの作成
自分でガリガリ実装するというのも良いとは思うのですが、できればライブラリを利用してサクッと作成したい。
ライブラリを探した所、liboauth2が使用できそうです。
で早速作成した処理が以下の通り。
というか、liboauth2のソースから抜き出しただけと言えばだけなのですが...
oauth2_log_t* log = oauth2_init(OAUTH2_LOG_TRACE1, 0);
char* pkce = oauth2_rand_str(log, OAUTH2_PKCE_LENGTH); // code_verifier
unsigned char *dst = NULL;
unsigned int dst_len = 0;
oauth2_jose_hash_bytes(
log,
"sha256",
(const unsigned char *)pkce,
strlen(pkce),
&dst,
&dst_len
);
char *code_challenge;
oauth2_base64url_encode(log, dst, dst_len, &code_challenge); // code_challenge
oauth2_mem_free(pkce);
oauth2_shutdown(log);
こんな感じで値のペアが取得できたと思います。
Windowsでliboauth2をビルド
公開されているソースのおかげで処理自体はサクッと作成できるのですが、問題はliboauth2がWindowsでビルドできないということです。
linuxであれば、そもそもビルドする必要もなく、apt install ...でビルド済みバイナリが手に入るわけですが、日ごろ使いなれている、Windowsでもビルドできる状況を維持したい。
依存関係のcjoseとjanssonはビルドできたのですが、liboauth2は機能が多く、全てビルドするのは手間が掛かると思われ。
OAuth関連で、上記に記述した部分以外にも、もう少し使えそうなコードもあるのですが、それらは実装済みなので、無理に使う必要もなく。
使いたい処理は上記の部分だけ。
そして、それだけなら、なんとかビルドすることができました。
Apache2やMITライセンスとは
もちろんソースは利用してよいと思われ、抽出して利用しているという事も、なんらか明記すれば良いとは思うのですが、一部のソースだけ抽出してビルドするというのは、何か人のソースを盗んだような少しだけ後ろめたい気持ちにもなる今日この頃です。
Windowsで実験するとき用に、これらの部分だけ別のDLLにまとめておいて、ソース自体を自分のソースツリーに含めなければ良いのかなと考えています。
おわりに
PKCEの仕組みを追加できれば、当初実装しようと考えていた部分の実装が終わります。
一旦これでリリースとしてREADMEの記述など、仕上げていきたいと思います。