Tailscale Serveとは何か、調べてみた
自宅のMac miniで動かしているローカルLLMサーバーに、外出先のiPhoneやWindows PCから安全にアクセスしたいと思い、「Tailscale Serve」という機能について調べてみました。VPNの知識があまりなくても理解できるように、基本の仕組みから実際の設定・運用でつまずいたポイントまで整理してみます。
Tailscale Serveとは
Tailscale Serveは、Tailscaleのネットワーク(tailnet)内で動いているローカルのWebサービスを、同じネットワークに参加している他のデバイスから安全にアクセスできるようにする機能です。
tailscale serve コマンドで、ローカルの特定ポート(例:localhost:8080)をHTTPS経由で公開できる
自動でTLS証明書が発行され、https://マシン名.tailnet名.ts.net のようなURLでアクセス可能になる
公開範囲はデフォルトでtailnet内のみ。同じネットワークに参加しているデバイスだけがアクセスできる
似た機能に「Funnel」がありますが、こちらはtailnetの外(インターネット)にも公開できる拡張版です。「身内だけに見せたいならServe、外にも公開したいならFunnel」というイメージで使い分けると分かりやすいです。
証明書についても、Let's Encryptを自分で設定して90日ごとに更新…という作業は不要で、Tailscaleが裏側で発行・更新を自動でやってくれます。管理画面でHTTPS機能さえ有効にしておけば、tailscale serve を実行した時点で証明書取得まで自動で走ります。
tailnetに「参加する」とはどういうことか
Tailscaleは、WireGuardという技術をベースにしたプライベートな仮想ネットワーク(tailnet)を作る仕組みです。
各デバイスにTailscaleアプリを入れて、同じアカウントでログインする
するとそのデバイスに 100.x.x.x 形式のプライベートIPが割り振られる
物理的な場所に関係なく、同じtailnetに参加しているデバイス同士は、まるで同じLAN内にいるかのように通信できる
イメージとしては、iPhoneのTailscaleアプリでログイン(VPN接続を確立)しておけば、あとは普段使っているブラウザから https://マシン名.tailnet名.ts.net にアクセスするだけで、自宅サーバーのサービスに届く、という2段構えの仕組みです。Tailscaleアプリ自体は「接続のスイッチ」のような役割で、毎回操作する必要はありません。
なぜ「安全」と言えるのか、仕組みを深掘り
Tailscale Serveが安全とされる理由は、大きく「そもそも繋がらない」レイヤーと「繋がっても中身が読めない」レイヤーの2段階に分けて考えると分かりやすいです。
各デバイスが自分で鍵ペアを生成する:Tailscaleにログインすると、そのデバイス自身が公開鍵・秘密鍵のペアをローカルで自動生成する。鍵をTailscale側から配られるのではなく、デバイス側で作られるのがポイント。秘密鍵はデバイスの外に一切出ない
公開鍵だけをコーディネーションサーバーに登録:生成した公開鍵を、Tailscaleの管理サーバー(コーディネーションサーバー)に登録する。秘密鍵は登録されないので、Tailscale側のサーバーでも通信内容を復号することはできない
コーディネーションサーバーが「ネットマップ」を配る:tailnet内の全デバイスの公開鍵とIPアドレス情報をまとめた「ネットマップ」を、そのtailnetに参加しているデバイスにだけ配布する。参加していないデバイスは、誰がどのIPにいるかという情報自体を受け取れない。役割としては通信の中継役ではなく、あくまで「マッチメイカー」に近い立ち位置
WireGuardで直接、暗号化トンネルを張る:実際の通信は、ネットマップをもとにデバイス同士が直接WireGuardの暗号化トンネルを確立する。正しい鍵ペアを持っていないデバイスは、IPアドレス(100.x.x.x)を知っていても暗号化の握手(ハンドシェイク)が成立せず、接続自体が確立しない
そもそもIPアドレスが外部から到達不能:Tailscaleの100.x.x.xというIPアドレス帯は通常のインターネットからルーティングされない特殊な範囲。tailnetに参加していないデバイスからは、そのIPへの経路自体が存在しない
HTTPSはその上にさらに重なる層:ここまでで「参加者以外は到達すらできない」状態がすでにできているが、Serveが提供するHTTPS(TLS)は、その上でさらに通信内容自体を暗号化する層。同じtailnet内であっても、経路上の盗聴・改ざんを防ぐ意味がある
整理すると、鍵生成(デバイス側)→登録(公開鍵のみ)→到達可能性の制御(ルーティングされないIP空間)→暗号化トンネル(WireGuard)→さらにHTTPS(TLS) という何重もの仕組みが組み合わさって成立しています。URLを知られないようにするといった曖昧な仕組みではなく、ネットワーク経路のレベルで根本的に遮断されているのが特徴だと感じました。ポート開放やngrokのように「とりあえず外に穴を開ける」方式と比べると、攻撃の対象になりうる経路そのものがtailnet参加者以外には存在しない点が本質的な違いです。
料金は?
個人利用なら基本的に無料です。
Personal(無料)プラン:最大6ユーザー、デバイス数は無制限。個人のホームラボ用途(自宅サーバーとスマホ・PCを繋ぐなど)なら、Serveなどの機能も含めてこの範囲で十分
有料プラン:チームや組織向け。2026年4月の料金改定で座席課金制になり、SSO連携やアクセス制御の高度化、監査ログなどが必要な場合に検討する位置づけ
実際にMac miniとiPhoneで設定してみる
理屈がわかったところで、実際にMac miniで動かしているサーバー(ローカルの8080番ポート想定)をiPhoneから見られるようにする設定手順もまとめておきます。
Mac mini側
Tailscaleをインストール:Homebrewの場合は brew install tailscale。公式サイトから.pkgをダウンロードしてもOK
ログインしてtailnetに参加:sudo tailscale up を実行するとブラウザが開き、Googleアカウントなどでログイン(サインアップ)する
HTTPS機能を有効化(初回のみ、管理画面から):Tailscale管理画面(https://login.tailscale.com/admin/dns )の「DNS」タブで「HTTPS Certificates」を有効にする。これはCLIコマンドが用意されておらず、管理画面からの操作が必須。やっておかないとServeが証明書を発行できずエラーになる
Serveでポートを公開:tailscale serve --bg 8080 のように実行する。--bg を付けるとバックグラウンドで動き続ける
公開URLを確認:tailscale serve status で、https://マシン名.tailnet名.ts.net のようなURLが表示される。これが外部からのアクセス先
Homebrewでインストールした場合のつまずきポイント
Homebrewで brew install tailscale を実行してCLIを入れた場合、そのまま sudo tailscale up を叩くと以下のようなエラーが出ることがあります。
failed to connect to local Tailscale service; is Tailscale running?
これは、Tailscale本体(バックグラウンドで動く tailscaled というサービス)がまだ起動していないために出るエラーです。Homebrew版はCLIだけが入る形なので、サービスとして起動する作業が別途必要でした。対処法は、Homebrewのサービス機能で起動することです。
sudo brew services start tailscale
これで tailscaled がバックグラウンドで起動します。その後、改めて sudo tailscale up を実行すると、今度は認証用のURLが表示されます。表示されたURL(https://login.tailscale.com/a/xxxxxxxxx のような形式)をブラウザで開き、GoogleやGitHubなどのアカウントでログインすれば認証完了です。完了したかどうかは tailscale status で確認でき、自分のMac miniが 100.x.x.x のIPと共に表示されていれば無事tailnetに参加できています。
再起動しても設定が自動で復元される理由
一度Serveの設定(tailscale serve --bg --https=8440 8000 など)を入れると、Mac miniを再起動しても手動でコマンドを打ち直す必要がないことに気づきました。これは2つの仕組みが組み合わさっているためです。
brew services startが自動起動も設定していた:sudo brew services start tailscale を実行すると、単に今すぐ起動するだけでなく、macOSのlaunchd(起動管理の仕組み)に登録され、Mac起動時に自動でtailscaledが立ち上がるようになる。つまりMacの電源が落ちればプロセス自体は一旦消えるが、次の起動時にlaunchdが自動的に立て直してくれる
Serveの設定はディスクに永続化されている:tailscale serve で設定したルール(どのポートをどう公開するか)は、tailscaledのメモリ上だけでなく永続的な状態ファイルとしてディスクに保存される
再起動時の流れをまとめると、Macが起動 → launchdがtailscaledを自動起動 → tailscaledが起動時にディスク上の過去の設定(Serveのルールを含む)を読み込んで復元、という順序です。結果として、コマンドを打ち直さなくても元のURLが再び使える状態になります。もし自動起動自体を止めたい場合は、sudo brew services stop tailscale で登録を解除できます。
iPhone側
App StoreでTailscaleアプリをインストール
Mac miniと同じアカウントでログインする。これでiPhoneも同じtailnetに参加する
初回、「VPN構成の追加」の許可を求められるので許可する。以降は裏側で常時接続される状態になる
あとは普通にSafariでMac miniのServe URLを開くだけ
「VPN構成の追加」の許可は、そのまま許可して問題ありません。Tailscaleは技術的にVPNの仕組み(WireGuardベースのトンネル)を使ってtailnet内の通信を実現しているため、iOSの標準的な確認として表示されるものです。VPN機能を持つアプリ全般で出るメッセージであり、Tailscale固有の話ではありません。
一般的な「VPNアプリ」のように通信内容を第三者サーバーが中継・閲覧するものとは違う点にも注意が必要です。Tailscaleは基本的にtailnet内のデバイス同士を直接つなぐためだけにこの仕組みを使っており、Web検索やSNS利用などtailnet外への通信には影響しません。許可しないとそもそもtailnetに参加できず、Mac miniへのアクセス自体ができなくなります。ログインに使うアカウントがMac mini側と同じであることも確認しておくと安心です。違うアカウントだと別のtailnetになってしまい、繋がりません。なお許可は「設定 → VPN」からいつでも取り消せます。
つまずきやすいポイントまとめ
Mac miniがスリープしているとそもそもアクセスできないので、スリープ防止(pmset)の設定が効いてくる
HTTPS Certificatesの有効化を忘れると、tailscale serve実行時にエラーと有効化用URLが表示されるので、その指示に従えば解決する
同じポート番号をServeとFunnelで同時には使えない(後から設定した方で上書きされる)。Funnelを使わないなら気にしなくて良い
複数のWebアプリを同時に公開する方法
Mac miniで複数のポート(たとえば8000番と8001番)でそれぞれ別のWebアプリを動かしている場合、Serveは1台のデバイスで複数ポートをまとめて公開できることも分かりました。方法は大きく2通りあります。
パスを分ける方法(シンプル)
tailscale serve --bg --set-path /app1 http://localhost:8000
tailscale serve --bg --set-path /app2 http://localhost:8001
これで https://マシン名.tailnet名.ts.net/app1 と /app2 のようにアクセスできます。
ポート番号を分ける方法
tailscale serve --bg --https=8443 http://localhost:8000
tailscale serve --bg --https=8444 http://localhost:8001
この場合は https://マシン名.tailnet名.ts.net:8443 と :8444 のようにアクセスします。
デフォルトのHTTPSポート(443番、URLにポート番号を書かなくていい形)は1つのパス構成につき1回しか使えないため、両方ともポート番号なしのすっきりしたURLにしたい場合は、パスを分ける方法の方が扱いやすそうです。現在公開中の設定は tailscale serve status でいつでも確認できるので、複数アプリを動かすようになったらこのコマンドで状況を把握しておくと安心です。
サービスの止め方
Homebrewのbrew servicesで起動した場合、止め方は2種類あります。
一時的にtailnetへの接続だけ切りたい場合は sudo tailscale down で十分です。通信は切れますが、tailscaled自体はバックグラウンドで動き続けます。再接続したいときは sudo tailscale up で戻せます。
tailscaledのプロセスごと完全に止めたい場合(自動起動の登録も解除したい場合)は、以下のようにHomebrewのサービス機能を使います。
sudo brew services stop tailscale
停止できているかは brew services list で確認でき、tailscaleの行がstoppedになっていればOKです。
まとめると、tailscale downは接続だけ切る(プロセスは生きている)、brew services stop tailscaleはプロセスごと止める(自動起動もオフ)という違いがあります。普段はMac miniを常時起動させておいてtailscale down/upで接続を出し入れする方が扱いやすく、完全停止はTailscale自体をしばらく使わないときくらいで十分そうです。
まとめ
Tailscale Serveは、ローカルのWebサービスをtailnet内に安全に公開できる機能
安全な理由は、各デバイスが独自に鍵ペアを生成し、参加者にしかネットマップが配られず、WireGuardの暗号化トンネルとHTTPSが何重にも重なっているため
証明書の発行・更新は自動だが、tailnet全体のHTTPS機能の有効化自体は管理画面からの操作が必要
Homebrewでインストールした場合、tailscaledのサービス起動やlaunchdへの自動起動登録はbrew services経由で行う。Serve設定はディスクに永続化されるので、再起動後も自動で復元される
1台のデバイスで複数のWebアプリを、パスやポート番号を分けて同時に公開することも可能
個人のホームラボ用途なら無料プランで十分カバーできる
自宅サーバーへのリモートアクセスというと、以前はngrokのようなトンネリングツールやポート開放を検討していましたが、Tailscaleならネットワーク接続の延長線上でHTTPS公開までできる点が便利だと感じました。