はじめに
クラウドリソースを使うとお金がかかる。
ローカルにシステム構築を行い、クラウドにはシステムへのエンドポイントを設置するだけの構成にすることで費用削減を狙う。
使用するもの
-
oauth2_proxy
IDaaSとの中継を行う -
nginx
リバースプロキシ -
ngrok
ネットワーク内部にあるローカルサーバのポート(ローカルホスト)に外部から直接アクセスすることを可能にするトンネリング/リバース・プロキシツール
https://ngrok.com/ -
auth0
IDaaS
https://auth0.com/
システム構成
app1(8001) / app2(8002) -> oauth_proxy(4180) -> nginx(8081, 8082) -> ngrok -> endpoint(randam1, randam2)
endpoint
└─nginx
└─oauth2_proxy
├─auth0
└─app
環境構築
- Windows 10
構築方法
- 最終的に下記のフォルダ構成となる。
C:.
└─Project
├─app1
│ └─index.html
├─app2
│ └─index.html
├─nginx(必要な部分のみ記載)
│ ├─conf
│ │ └─nginx.conf
│ └─nginx.exe
├─oauth2_proxy
│ ├─oauth2-proxy.exe
│ └─oauth2-proxy.cfg
└─ngrok
└─ngrok.exe
"%HOMEPATH%\AppData\Local\ngrok\ngrok.yml"
>https://ngrok.com/docs/ngrok-agent/config
- app1やapp2は簡単に用意する
<!doctype html>
<html>
<head>
<title>app1</title>
</head>
<body>
<p>本文</p>
</body>
</html>
<!doctype html>
<html>
<head>
<title>app2</title>
</head>
<body>
<p>本文</p>
</body>
</html>
- コマンドプロンプト(cmd1, cmd2)を二つ起動し、HTTPサーバー(app)を二つ起動する
C:\Project\app1> python -m http.server 8001
C:\Project\app2> python -m http.server 8002
Python 3.x
$ python -m http.server 8000
参考:https://gist.github.com/willurd/5720255
- nginxをダウンロードし、上記のフォルダに配置する。
- nginx.confを設定する。
#user nobody;
worker_processes 1;
#error_log logs/error.log;
#error_log logs/error.log notice;
#error_log logs/error.log info;
#pid logs/nginx.pid;
events {
worker_connections 1024;
}
http {
include mime.types;
default_type application/octet-stream;
#log_format main '$remote_addr - $remote_user [$time_local] "$request" '
# '$status $body_bytes_sent "$http_referer" '
# '"$http_user_agent" "$http_x_forwarded_for"';
#access_log logs/access.log main;
sendfile on;
#tcp_nopush on;
#keepalive_timeout 0;
keepalive_timeout 65;
#gzip on;
server {
listen 8081;
server_name localhost;
#charset koi8-r;
#access_log logs/host.access.log main;
location /oauth2/ {
proxy_pass http://127.0.0.1:4180;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Scheme $scheme;
proxy_set_header X-Auth-Request-Redirect http://127.0.0.1:8001;
# or, if you are handling multiple domains:
# proxy_set_header X-Auth-Request-Redirect $scheme://$host$request_uri;
}
location = /oauth2/auth {
proxy_pass http://127.0.0.1:4180;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Scheme $scheme;
# nginx auth_request includes headers but not body
proxy_set_header Content-Length "";
proxy_pass_request_body off;
}
location / {
auth_request /oauth2/auth;
error_page 401 = /oauth2/sign_in;
# pass information via X-User and X-Email headers to backend,
# requires running with --set-xauthrequest flag
auth_request_set $user $upstream_http_x_auth_request_user;
auth_request_set $email $upstream_http_x_auth_request_email;
proxy_set_header X-User $user;
proxy_set_header X-Email $email;
# if you enabled --pass-access-token, this will pass the token to the backend
auth_request_set $token $upstream_http_x_auth_request_access_token;
proxy_set_header X-Access-Token $token;
# if you enabled --cookie-refresh, this is needed for it to work with auth_request
auth_request_set $auth_cookie $upstream_http_set_cookie;
add_header Set-Cookie $auth_cookie;
# When using the --set-authorization-header flag, some provider's cookies can exceed the 4kb
# limit and so the OAuth2 Proxy splits these into multiple parts.
# Nginx normally only copies the first `Set-Cookie` header from the auth_request to the response,
# so if your cookies are larger than 4kb, you will need to extract additional cookies manually.
auth_request_set $auth_cookie_name_upstream_1 $upstream_cookie_auth_cookie_name_1;
# Extract the Cookie attributes from the first Set-Cookie header and append them
# to the second part ($upstream_cookie_* variables only contain the raw cookie content)
if ($auth_cookie ~* "(; .*)") {
set $auth_cookie_name_0 $auth_cookie;
set $auth_cookie_name_1 "auth_cookie_name_1=$auth_cookie_name_upstream_1$1";
}
# Send both Set-Cookie headers now if there was a second part
if ($auth_cookie_name_upstream_1) {
add_header Set-Cookie $auth_cookie_name_0;
add_header Set-Cookie $auth_cookie_name_1;
}
proxy_pass http://127.0.0.1:8001/;
}
server {
listen 8082;
server_name localhost;
#charset koi8-r;
#access_log logs/host.access.log main;
location /oauth2/ {
proxy_pass http://127.0.0.1:4180;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Scheme $scheme;
proxy_set_header X-Auth-Request-Redirect http://127.0.0.1:8002;
# or, if you are handling multiple domains:
# proxy_set_header X-Auth-Request-Redirect $scheme://$host$request_uri;
}
location = /oauth2/auth {
proxy_pass http://127.0.0.1:4180;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Scheme $scheme;
# nginx auth_request includes headers but not body
proxy_set_header Content-Length "";
proxy_pass_request_body off;
}
location / {
auth_request /oauth2/auth;
error_page 401 = /oauth2/sign_in;
# pass information via X-User and X-Email headers to backend,
# requires running with --set-xauthrequest flag
auth_request_set $user $upstream_http_x_auth_request_user;
auth_request_set $email $upstream_http_x_auth_request_email;
proxy_set_header X-User $user;
proxy_set_header X-Email $email;
# if you enabled --pass-access-token, this will pass the token to the backend
auth_request_set $token $upstream_http_x_auth_request_access_token;
proxy_set_header X-Access-Token $token;
# if you enabled --cookie-refresh, this is needed for it to work with auth_request
auth_request_set $auth_cookie $upstream_http_set_cookie;
add_header Set-Cookie $auth_cookie;
# When using the --set-authorization-header flag, some provider's cookies can exceed the 4kb
# limit and so the OAuth2 Proxy splits these into multiple parts.
# Nginx normally only copies the first `Set-Cookie` header from the auth_request to the response,
# so if your cookies are larger than 4kb, you will need to extract additional cookies manually.
auth_request_set $auth_cookie_name_upstream_1 $upstream_cookie_auth_cookie_name_1;
# Extract the Cookie attributes from the first Set-Cookie header and append them
# to the second part ($upstream_cookie_* variables only contain the raw cookie content)
if ($auth_cookie ~* "(; .*)") {
set $auth_cookie_name_0 $auth_cookie;
set $auth_cookie_name_1 "auth_cookie_name_1=$auth_cookie_name_upstream_1$1";
}
# Send both Set-Cookie headers now if there was a second part
if ($auth_cookie_name_upstream_1) {
add_header Set-Cookie $auth_cookie_name_0;
add_header Set-Cookie $auth_cookie_name_1;
}
proxy_pass http://127.0.0.1:8002/;
}
#error_page 404 /404.html;
# redirect server error pages to the static page /50x.html
#
error_page 500 502 503 504 /50x.html;
location = /50x.html {
root html;
}
}
}
- ngrokにアカウント登録する。
説明後日追記
- ngrokをダウンロードし、上記のフォルダに配置する。
- ngrok.ymlを下記のように修正する。
version: "2"
authtoken: *******************************************
tunnels:
app1:
addr: 8081
proto: http
app2:
addr: 8082
proto: http
- auth0にアカウント登録する。
説明後日追記
- oauth0_proxyをダウンロードする。
## <addr>:<port> to listen on for HTTP/HTTPS clients
http_address = "127.0.0.1:4180"
provider = "oidc"
# oidc_issuer_url = "https://${Auth0>Applications>Settings>Basic Information>Domain}"
oidc_issuer_url = "https://xxxxx.jp.auth0.com/"
## the OAuth Redirect URL.
# redirect_url = "https://${ngrokで公開したドメイン名}/oauth2/callback"
redirect_url = "https://xxxxx.jp.ngrok.io/oauth2/callback"
## the http url(s) of the upstream endpoint. If multiple, routing is based on path
upstreams = [
"https://${ngrokで公開したドメイン名}"
]
email_domains = [
"*"
]
## The OAuth Client ID, Secret
# client_id = "${Auth0>Applications>Settings>Basic Information>Client ID}"
client_id = "***************"
# client_secret = "${Auth0>Applications>Settings>Basic Information>Client Secret}"
client_secret = "************************************************"
## Cookie Settings
cookie_name = "_oauth2_proxy"
cookie_secret = "**************************************"
試してみる
C:\Project\nginx>start nginx
C:\Project\ngrok>ngrok start app1 app2
C:\Project\oauth2_proxy> oauth2_proxy.exe --config=oauth2_proxy.cnf
サービスに登録する
サービスに登録することで、システムが稼働しているPCの予期せぬシャットダウンがあった場合に
電源投入で再稼働させることができる。
- nssmをダウンロードする。PATHが通った位置に配置
nssm install nginx
nssm set nginx Application C:\Project\nginx\nginx.exe
nssm set nginx AppDirectory C:\Project\nginx
nssm set nginx AppParameters "start nginx"
nssm install ngrok
nssm set ngrok Application C:\Project\ngrok\ngrok.exe
nssm set ngrok AppDirectory C:\Project\ngrok
nssm install oauth2_proxy
nssm set oauth2_proxy Application C:\Project\oauth2_proxy\oauth2_proxy.exe
nssm set oauth2_proxy AppDirectory C:\Project\oauth2_proxy
nssm set oauth2_proxy AppParameters "--config='C:\Project\oauth2_proxy\oauth2_proxy.cfg'"
その他
ngrokが無料プランだとngrok起動のたびに外部IPが変わってしまうため、
その都度ngrokのWEBダッシュボードよりURLを確認し、下記を設定する必要がある。
- Auth0>Applications>Settings>Application URIs>Application Login URI
- Auth0>Applications>Settings>Application URIs>Allowed Callback URLs
- oauth2_proxy.cfg>redirect_url