🦑

VMwareとRocky Linuxで実践:仮想環境におけるプロキシサーバの構築と検証

2023/10/05に公開

はじめに

本記事では、VMware Workstation Player 16を使用してRocky Linux9上にプロキシサーバ(squid)を構築する手順を解説します。

多くの大規模システムの本番環境で、プロキシサーバを経由してのインターネット接続が一般的であり、サーバ構築の実務でも何度か経験しました。ネットワーク運用やセキュリティの観点からプロキシサーバの役割と設定方法の基本を理解し、実践的な知識を得る目的で今回記事にしてみました。
 

プロキシサーバの役割

  • キャッシング: よくアクセスされるリソースをキャッシュして、レスポンスを高速化し帯域幅を節約。
  • フィルタリング: 外部からの攻撃(例:マルウェア、フィッシング等)をブロック。
  • プライバシー: クライアントの実際のIPや情報を外部に露出させない。
  • 帯域制限: ネットワークの帯域幅の利用を均等化や制限。
  • ログ取得: 外部へのリクエストや応答ログを取得し、ネットワークの利用状況を分析。
     

記事の取り組み内容

  • プロキシサーバ(squid)の構築手順を学ぶ。
  • クライアントからプロキシサーバ(squid)を通じてインターネットに接続する方法を理解する。
  • プロキシサーバ(squid)のsyslogを用いて接続の検証を行う。
  • 検証結果をログとして詳細に確認する方法を学ぶ。
     

概略

  1. プロキシサーバ(Squid)の構築
  2. クライアントよりプロキシサーバ(squid)を経由してインターネットに接続
  3. プロキシサーバ(Squid)のsyslogで検証
     

検証環境

本検証は、ホストPCと2つの仮想マシン間で実施されています。仮想マシンのネットワーク接続はNATモードを採用し、ホストPCを介しています。

  • ホストOS: Windows 10
  • 仮想化ソフトウェア: VMware Workstation Player 16

仮想マシンの詳細

  • ゲストOS (プロキシサーバ): Rocky Linux 9
  • ゲストOS (クライアントサーバ): Rocky Linux 9

この構成により、1つの仮想マシンがプロキシサーバとして、もう1つの仮想マシンがクライアントサーバとして機能します。

 

1. プロキシサーバ(Squid)の構築

1-1. Squidのインストール

Rocky LinuxにてSquidをインストールします。

dnf install squid

 

1-2. Squidの設定(acl等)

Squidの設定ファイルは /etc/squid/squid.conf にあります。以下のコマンドで内容を確認できます。この検証では、設定ファイルの内容をそのまま使用しますが、一部の設定項目について補足を追加しています。

[username@xx ~]# cat /etc/squid/squid.conf/etc/squid/squid.conf

#
# Recommended minimum configuration:
#

# Example rule allowing access from your local networks.
# Adapt to list your (internal) IP networks from where browsing
# should be allowed
acl localnet src 0.0.0.1-0.255.255.255	# RFC 1122 "this" network (LAN)
acl localnet src 10.0.0.0/8		# RFC 1918 local private network (LAN)
acl localnet src 100.64.0.0/10		# RFC 6598 shared address space (CGN)
acl localnet src 169.254.0.0/16 	# RFC 3927 link-local (directly plugged) machines
acl localnet src 172.16.0.0/12		# RFC 1918 local private network (LAN)
acl localnet src 192.168.0.0/16		# RFC 1918 local private network (LAN)
acl localnet src fc00::/7       	# RFC 4193 local private network range
acl localnet src fe80::/10      	# RFC 4291 link-local (directly plugged) machines

acl SSL_ports port 443
acl Safe_ports port 80		# http
acl Safe_ports port 21		# ftp
acl Safe_ports port 443		# https
acl Safe_ports port 70		# gopher
acl Safe_ports port 210		# wais
acl Safe_ports port 1025-65535	# unregistered ports
acl Safe_ports port 280		# http-mgmt
acl Safe_ports port 488		# gss-http
acl Safe_ports port 591		# filemaker
acl Safe_ports port 777		# multiling http

#
# Recommended minimum Access Permission configuration:
#
# Deny requests to certain unsafe ports
http_access deny !Safe_ports
#定義されたSafe_ports以外のポートへのアクセスを拒否します。

# Deny CONNECT to other than secure SSL ports
http_access deny CONNECT !SSL_ports
#SSL_ports以外のポートへのCONNECTメソッドを使用したアクセスを拒否します。これは、主に不正なトンネリングを防ぐためのものです。

# Only allow cachemgr access from localhost
http_access allow localhost manager
http_access deny manager

# We strongly recommend the following be uncommented to protect innocent
# web applications running on the proxy server who think the only
# one who can access services on "localhost" is a local user
#http_access deny to_localhost

#
# INSERT YOUR OWN RULE(S) HERE TO ALLOW ACCESS FROM YOUR CLIENTS
#

# Example rule allowing access from your local networks.
# Adapt localnet in the ACL section to list your (internal) IP networks
# from where browsing should be allowed
http_access allow localnet
#[acl localnet src~]で定義したlocalnet(プライベートアドレス範囲)からのアクセスを許可します。

http_access allow localhost
#プロキシサーバ自体からのアクセスを許可します。

# And finally deny all other access to this proxy
http_access deny all

# Squid normally listens to port 3128
http_port 3128
#Squidがリッスンするポートを3128に設定しています。

# Uncomment and adjust the following to add a disk cache directory.
#cache_dir ufs /var/spool/squid 100 16 256

# Leave coredumps in the first cache dir
coredump_dir /var/spool/squid

#
# Add any of your own refresh_pattern entries above these.
#

設定を変更した際は、Squidを再起動して設定の変更を反映させる必要があります。

systemctl restart squid

 

1-3. ファイアウォールの設定と確認

ファイアウォールの状態を確認します。「Active: active (running)」となっています。

[username@xx ~]systemctl status firewalld

● firewalld.service - firewalld - dynamic firewall daemon
     Loaded: loaded (/usr/lib/systemd/system/firewalld.service; enabled; preset>
     Active: active (running) since Wed 2023-08-30 15:07:46 JST; 6 days ago
       Docs: man:firewalld(1)
   Main PID: 917 (firewalld)
      Tasks: 4 (limit: 10804)
     Memory: 31.3M
        CPU: 3.874s
     CGroup: /system.slice/firewalld.service
             mq917 /usr/bin/python3 -s /usr/sbin/firewalld --nofork --nopid

Squidのポート(通常は3128)を許可します。

firewall-cmd --zone=public --add-port=3128/tcp --permanent

リロードし変更を反映します。

firewall-cmd --reload

 

1-4. Squidの動作確認と設定

Squidの動作状態を確認するには以下のコマンドを実行します。

[username@xx ~]#systemctl status squid

● squid.service - Squid caching proxy
     Loaded: loaded (/usr/lib/systemd/system/squid.service; enabled; preset: di>
     Active: active (running) since Wed 2023-09-06 16:05:41 JST; 4 weeks 0 days>
       Docs: man:squid(8)

もしSquidが稼働していない場合、次のコマンドで起動します。

systemctl start squid

システムの起動時にSquidを自動起動するように設定するには以下のコマンドを実行します。

systemctl enable squid

 

1-5. ポートのリッスン状態確認

プロキシサーバのポート(3128)で待ち受けているかを、「netstat」、「ss」コマンドで確認します。

[username@xx ~]#netstat -tuln | grep 3128
tcp6       0      0 :::3128                 :::*                    LISTEN

#もしくは

[username@xx ~]#ss -tuln | grep 3128
tcp   LISTEN 0      4096               *:3128             *:*

LISTEN状態であることが確認できました。
以上で、プロキシサーバの基本的な設定と動作確認が完了です。

 

2.クライアントよりプロキシサーバ(squid)を経由してインターネットに接続

クライアント側の設定を行います。今回の検証では、クライアントもRocky Linuxを使用します。
 

2-1. 環境変数の設定

export コマンドを使用して、プロキシ接続に関する環境変数を設定します。これにより、現在のセッション内でのみ、指定したプロキシサーバを経由して外部ネットワークにアクセスします。

http_proxy はHTTPトラフィック用、https_proxy はHTTPSトラフィック用の変数ですが、どちらも同じプロキシサーバのアドレスを指定します。

export http_proxy=http://192.168.111.130:3128
export https_proxy=http://192.168.111.130:3128

 

2-2. 永続的な設定

テストが成功して環境変数を永続的に適用したい場合は、ユーザーの ~/.bashrc、~/.bash_profile または ~/.profile などのファイルに上記の変数定義を追加します。
 

2-3. 接続テスト

外部のウェブサイトやサービスへの接続をテストします。curl コマンドを利用して、外部のウェブページの内容を取得することができます。

curl http://www.google.com

コマンド実行結果は以下です。

[username@xx ~]# curl http://www.google.com
<!doctype html><html itemscope="" itemtype="http://schema.org/WebPage" lang="ja"><head><meta content= 以下省略

これにより、クライアントがプロキシサーバを経由して正常に外部のウェブサイトにアクセスできることが確認できました。
 

3. プロキシサーバ(Squid)のsyslogで検証

 

3-1. アクセスログの確認方法

Squidのアクセスログの場所はデフォルト設定では、/var/log/squid/access.log にあります。このログの内容を確認するには以下のコマンドを使用します。

cat /var/log/squid/access.log

 

3-2.アクセスログの検証結果

以下は、クライアント(IPアドレス:192.168.111.8)がプロキシサーバを経由してアクセスした実際のログの一例です。

[username@xx ~]# cat /var/log/squid/access.log
1693985358.850    313 192.168.111.8 TCP_MISS/200 22058 GET http://www.google.com/ - HIER_DIRECT/172.217.26.228 text/html
1693985489.086    230 192.168.111.8 TCP_MISS/200 1227 HEAD http://www.google.com/ - HIER_DIRECT/142.251.42.132 text/html
1693986329.451    270 192.168.111.8 TCP_MISS/200 22110 GET http://www.google.com/ - HIER_DIRECT/142.251.42.132 text/html
1693986372.654    155 192.168.111.8 TCP_MISS/301 537 GET http://www.yahoo.co.jp/ - HIER_DIRECT/183.79.219.124 text/html
1693986414.510    221 192.168.111.8 TCP_TUNNEL/200 42784 CONNECT www.yahoo.co.jp:443 - HIER_DIRECT/183.79.219.124 -
1693986441.803    319 192.168.111.8 TCP_TUNNEL/200 6380 CONNECT www.yahoo.co.jp:443 - HIER_DIRECT/183.79.248.124 -

 

タイムスタンプ:1693985358.850

*クライアントのIPアドレス:192.168.111.8
*ステータスコードと要求のサイズ:TCP_MISS/200 22058
*リクエストのメソッド:GET
*要求されたURL:http://www.google.com/

クライアント(192.168.111.8)からのGETリクエストは、http://www.google.com/ に対して行われました。このリクエストはSquidのキャッシュに存在しなかったため(TCP_MISS)、直接オリジナルサーバ(172.217.26.228)にアクセスが行われ、正常な応答(HTTPステータスコード200)が返されました。この応答のサイズは22,058バイトでした。

 

タイムスタンプ:1693986414.510

*クライアントのIPアドレス:192.168.111.8
*ステータスコードと要求のサイズ:TCP_TUNNEL/200 42784
*リクエストのメソッド:CONNECT
*要求されたURL:www.yahoo.co.jp:443

クライアント(192.168.111.8)からの接続リクエストは、www.yahoo.co.jp の443ポート(HTTPS)に対して行われました。SquidはこのHTTPS接続のトンネルを確立しました(TCP_TUNNEL)。この接続は成功し(HTTPステータスコード200)、その接続におけるデータサイズは42,784バイトでした。なお、HTTPSの内容自体はSquidから見ることができません。

この解析を通して、クライアントはプロキシサーバを経由して、指定したURLにアクセスしていることが確認できました。

 

最後に

本記事ではプロキシサーバの構築に焦点を当てていますが、これはセキュリティの基本を学ぶ上で非常に役立つ内容だと感じました。また、ある程度の規模を持つインフラではプロキシは必須の技術となるため、個人の環境で構築し理解を深めることは役立つ場面も多くなるかと思います。

Discussion