2021.04.07

複数プロキシで冗長性対応する方法

こんにちは。次世代システム研究室のB.V.Mです。外国人で言葉遣いが間違いましたらご容赦ください。宜しくお願いします。

今期はネットワークインフラに関する作業していたので、プロキシを立ち上がる方法と複数プロキシを冗長化する方法を紹介したいと思います。

目次

  1. 課題
  2. Squidプロキシ設定
  3. DnsmasqでDNSの設定して冗長化
  4. 結果確認
  5. 参考リンク
  6. 最後に

1.課題

あるシステム内で、A(仮定:App)サーバーからC(仮定:CI)サーバーにアクセスしています。これからプロキシサーバーを経由してCサーバーへ接続するように修正必要です。

システムスペック:
  • OS:Centos7.4
  • プロキシツール:Squid3.5
  • DNSツール:Dnsmasq2.76
プロキシなし図

プロキシなしシステム



変更したいなのはAサーバーから内部プロキシサーバーを経由してCサーバーにアクセスします。

システムズ内部部プロキシ

内部部プロキシシステム



最後の目標:冗長性対応のため内部プロキシサーバーはP1サーバーとP2サーバに分けて冗長化されます。

冗長化対応のシステム

冗長化対応のシステム



冗長化(じょうちょうか)とは、システムの一部に何らかの障害が発生した場合に備えて、障害発生後でもシステム全体の機能を維持し続けられるように、予備装置を平常時からバックアップとして配置し運用しておくこと。冗長化によって得られる安全性は冗長性と呼ばれ、英語ではredundancyと呼ぶ。(Wikiにより)

2.Squidプロキシ設定

今回はSquidプロキシを設定いたします。
まずはyumをアップデートしてインストールします。
サーバーNP1とサーバーNP2は同じく実行されるので「NPx-server」というサーバー名でコマンドを実行します。インストールの際は単なる「yum install」です。
[user@NPx-server ~]sudo yum -y update
[user@NPx-server ~]sudo yum install -y squid
[user@NPx-server ~]squid -v
Squid Cache: Version 3.5.20
Service Name: squid
configure options:  '--build=x86_64-redhat-linux-gnu' '--host=x86_64-redhat-linux-gnu' '--program-prefix=' '--prefix=/usr' ...

設定

squid.confでsquidの設定を変更します。
[user@NPx-server ~]sudo vi /etc/squid/squid.conf

# デフォルトで内部IPが許可されます
acl localnet src 10.0.0.0/8     # RFC1918 possible internal network
acl localnet src 172.16.0.0/12  # RFC1918 possible internal network
acl localnet src 192.168.0.0/16 # RFC1918 possible internal network
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
acl CONNECT method CONNECT

#
# Safe_ports以外のポートにアクセスを許可されません
#
http_access deny !Safe_ports

# SSLポート以外は許可されない
http_access deny CONNECT !SSL_ports

# ローカルホストからのcachemgrアクセスのみを許可します
http_access allow localhost manager
http_access deny manager

# 「localhost」上のサービスにアクセスできるのはローカルユーザーだけだと考えるプロキシサーバーで
# 実行されている無実のWebアプリケーションを保護するために、
# 以下のコメントを外すことが勧められします。
http_access deny to_localhost

# ローカルネットワークからのアクセスを許可するルールの例。
# ACLセクションのlocalnetを適応させて、
# ブラウジングを許可する必要がある(内部)IPネットワークを一覧表示します
http_access allow localnet
http_access allow localhost

# 最後に、このプロキシへの他のすべてのアクセスを拒否します
http_access deny all
Firewallが設定されている場合3128を許可されるコマンドを実行必要です
[user@NPx-server ~]sudo firewall-cmd --permanent --add-port=3128/tcp
[user@NPx-server ~]sudo firewall-cmd --reload
Squidを制御するようのコマンド:
[user@NPx-server ~]sudo systemctl start squid
[user@NPx-server ~]sudo systemctl enable squid
Created symlink from /etc/systemd/system/multi-user.target.wants/squid.service to /usr/lib/systemd/system/squid.service.
# ログ確認用のコマンド
[user@NPx-server ~]sudo tail -fn 100 /var/log/squid/access.log
[user@NPx-server ~]sudo systemctl status squid
[user@NPx-server ~]sudo systemctl restart squid
[user@NPx-server ~]sudo systemctl stop squid

3.DnsmasqでDNSの設定しい冗長化

Dnsmasqは軽量で比較的容易に設定できるDNSサーバのフォワーダとDHCPサーバをもつソフトウェアである。(Wikiにより)
今回DNSサーバーとして使用しますのでDnsmasqのオプションとしてDHCP/TFTPサーバは調査致しません。

インストール

[user@A-server ~]$ yum install dnsmasq

設定

下記のように設定ファイルが変更必要です。
nsswitch.confファイルは、名前解決を行う優先順位を決めるファイルです。それでdnsの優先度を1番に修正します。
# 修正前
[user@A-server ~]$ cat /etc/nsswitch.conf | grep hosts:
hosts:      files dns myhostname
[user@A-server ~]$ sudo vi /etc/nsswitch.conf
# 修正後
[user@A-server ~]$ cat /etc/nsswitch.conf | grep hosts:
hosts:      dns files myhostname
resolv.confファイルは、システムのドメインネームシステムリゾルバーを構成するためのファイルです。ネームサーバーはロカール(127.0.0.1)を先に参照するように変更します。
# 修正前
[user@A-server ~]$ cat /etc/resolv.conf | grep nameserver
nameserver AA.BB.CC.DD
nameserver 127.0.0.1
[user@A-server ~]$ sudo vi /etc/resolv.conf | grep nameserver
# 修正後
[user@A-server ~]$ cat /etc/resolv.conf | grep nameserver
nameserver 127.0.0.1
nameserver AA.BB.CC.DD
hostsファイルは、ホスト名とIPアドレスを決めるのファイルです。
例えばプロキシサーバーのIPは下記のようになります。
NP1-server: AA.BB.CC.101
NP2-server: AA.BB.CC.102

その場合、Dnsmasqは/etc/hostsのホストを利用しますので、下記のようにプロキシサーバーのIPを追加します。
# 修正前
[user@A-server ~]$ sudo cat /etc/hosts
127.0.0.1   localhost localhost.localdomain 
::1         localhost localhost.localdomain 
[user@A-server ~]$ sudo vi /etc/hosts
# 修正後
[user@A-server ~]$ sudo cat /etc/hosts
127.0.0.1   localhost localhost.localdomain 
::1         localhost localhost.localdomain 
AA.BB.CC.101 squid_proxy
AA.BB.CC.102 squid_proxy
/etc/enviroment」ファイルのでプロキシ設定を下記のように追加します。
https_proxy=squid_proxy:3128
http_proxy=squid_proxy:3128
Dnsmasqを起動するようのコマンド:
sudo systemctl start dnsmasq
sudo systemctl status dnsmasq

結果確認

正常系

まずはNP1-serverとNP2-serverは両方動いている状態で確認します。(正常系)

正常系_冗長性_プロキシ

正常系



サーバーAのログ
[user@A-server ~]$ curl --trace traceToServerC_1 AA.BB.CC.DD:80
[user@A-server ~]$ less traceToServerC_1 
== Info: About to connect() to proxy squid_proxy port 3128 (#0)
== Info:   Trying AA.BB.CC.101...
== Info: Connected to squid_proxy (Trying AA.BB.CC.101) port 3128 (#0)
=> Send header, 130 bytes (0x82)
GET HTTP://AA.BB.CC.DD:80/ HTTP/1.1..User-Agent: curl/ Host: AA.BB.CC.DD..Accept: */*..Proxy-Connection: Keep-Alive.. ..
<= Recv header, 17 bytes (0x11) HTTP/1.1 200 OK.
ログを確認するとAA.BB.CC.101を経由してサーバーCへ接続成功でした。

異常系

異常系

異常系



サーバーAのログ
[user@A-server ~]$ sudo vi /etc/hosts
# 修正前 
[user@A-server ~]$ sudo cat /etc/hosts 127.0.0.1 
localhost localhost.localdomain ::1 
localhost localhost.localdomain 
AA.BB.CC.101 squid_proxy 
AA.BB.CC.102 squid_proxy
[user@A-server ~]$ sudo vi /etc/hosts 
# 修正後 
[user@A-server ~]$ sudo cat /etc/hosts 127.0.0.1 
localhost localhost.localdomain ::1 localhost 
localhost.localdomain 
AA.BB.CC.存在しないIP squid_proxy 
AA.BB.CC.102 squid_proxy
[user@A-server ~]$ sudo vi /etc/hosts
1番めのsquid_proxyが接続できない状態でCサーバーへ接続します。その場合2番めのsquid_proxyに自動的に経由してCサーバーへ接続はずです。
[user@A-server ~]$ curl --trace traceToC-server2 AA.BB.CC.DD:80
[user@A-server ~]$ less traceToC-server2 
== Info: About to connect() to proxy squid_proxy port 3128 (#0)
== Info:   Trying AA.BB.CC.101...
== Info: No route to host
== Info:   Trying AA.BB.CC.102..
== Info: Connected to squid_proxy (AA.BB.CC.102) port 3128 (#0)
=> Send header, 130 bytes (0x82)
GET HTTP://AA.BB.CC.DD:80/ HTTP/1.1..User-Agent: curl/ Host: AA.BB.CC.DD..Accept: */*..Proxy-Connection: Keep-Alive.. ..
<= Recv header, 17 bytes (0x11) HTTP/1.1 200 OK.
ログを確認するとNP1-server(AA.BB.CC.101)を接続するのが失敗したのでNP2-server(AA.BB.CC.102)を経由してサーバーCへ接続成功でした。

結論

この記事でSquidでプロキシを立ち上がって、Dnsmasqを利用して複数プロキシを冗長化仕方を紹介しました。小規模システムで設定が簡単で冗長性が対応できると思います。プロキシサーバーだけじゃなくて他のサーバーでも冗長性対応できると思いますので参考できればと思います。

参考リンク

最後に

次世代システム研究室では、グループ全体のインテグレーションを支援してくれるアーキテクトを募集しています。インフラ設計、構築経験者の方、次世代システム研究室にご興味を持って頂ける方がいらっしゃいましたら、ぜひ募集職種一覧からご応募をお願いします。 皆さんのご応募をお待ちしています。

  • Twitter
  • Facebook
  • はてなブックマークに追加

グループ研究開発本部の最新情報をTwitterで配信中です。ぜひフォローください。

 
  • AI研究開発室
  • 大阪研究開発グループ