すべてのプロダクト
Search
ドキュメントセンター

Alibaba Cloud Service Mesh:ASM のサーバーファーストプロトコルアプリケーションにおける接続問題の解決

最終更新日:Nov 06, 2025

Alibaba Cloud Service Mesh (ASM) で MySQL などのサーバーファーストプロトコルを使用するアプリケーションを実行すると、サイドカープロキシのプロトコル検出が原因で接続タイムアウトが発生する可能性があります。この問題を解決するには、TCP プロトコルを明示的に宣言して検出をバイパスします。サービスのデプロイシナリオに応じて、ポート名を変更したり、ServiceEntry を構成したり、mutual Transport Layer Security (mTLS) を無効にしたりできます。

タイムアウトの発生方法

SMTP、MySQL、DNS などのサーバーファーストプロトコルでは、TCP 接続が確立された後、サーバーが最初のデータパケットを送信する必要があります。

ASM サイドカープロキシでは、デフォルトでプロトコルの自動検出が有効になっています。これにより、サーバーファーストプロトコルの接続プロセスと競合が発生します。

  • サーバー側: サーバーのサイドカープロキシは、クライアントからの最初のパケットをインターセプトしてプロトコルを検出します。プロキシは、検出が完了するまでサーバーアプリケーションに接続を転送しません。

  • クライアント側: TCP ハンドシェイクの後、クライアントはサーバーが最初のデータパケットを送信するのを待ちます。クライアントはアプリケーションデータを送信しません。

サイドカープロキシは、クライアントがデータを送信してプロトコルを検出するのを待ちます。クライアントはサーバーからのデータを待ちますが、これはサイドカープロキシによってブロックされます。このデッドロックにより、クライアント接続がタイムアウトします。

シナリオ 1: クライアントとサーバーの両方がメッシュ内にある場合

サーバーが標準ポートを使用しない場合

  • 方法 1: サーバーに標準ポートを使用できます。ASM はこれらのポートを特別に処理するため、サイドカープロキシは接続をブロックしません。次の表に、一般的なサーバーファーストプロトコルアプリケーションの標準ポートを示します。

    プロトコル

    標準ポート

    MySQL

    3306

    SMTP

    25

    DNS

    53

    MongoDB

    27017

  • 方法 2: サーバーの YAML 構成を変更できます。ports.name にプレフィックス tcp- を追加します。次の YAML の例は、非標準ポート 3307 で実行される MySQL サービスの場合です。

    apiVersion: v1
    kind: Service
    metadata:
      name: my-mysql-svc
    spec:
      ports:
      - name: tcp-mysql-port
        port: 3307
        targetPort: 3307
      selector:
        app: my-mysql-server

サーバーが TLS 接続を使用しない場合

サーバーの TLS 接続を有効にできます。TLS ハンドシェイクでは、クライアントが最初に ClientHello メッセージを送信する必要があります。これにより、サイドカープロキシのプロトコル検出要件が満たされるため、プロキシは接続をブロックしません。

シナリオ 2: クライアントがメッシュ内にあり、サーバーがメッシュ外にある場合

  1. ASM で DNS プロキシ機能を有効にし、外部サービスにアクセスする必要があるすべてのクライアント Pod を再起動します。この操作により、プロキシ構成が適用されます。

  2. 外部サービス用に ServiceEntry リソースを作成できます。ポート定義で、protocolTCP として明示的に宣言します。

    この構成は、この外部サービスへのトラフィックをプレーンな TCP トラフィックとして扱うようにサイドカープロキシに指示します。これにより、プロトコル検出が回避されます。

    例: 外部 RDS for MySQL インスタンス用の ServiceEntry の作成

    ターゲットサービスのドメイン名は rm-xxxx.mysql.rds.aliyuncs.com で、ポートは 3306 です。

    apiVersion: networking.istio.io/v1
    kind: ServiceEntry
    metadata:
      name: external-mysql-rds
    spec:
      # 1. 外部サービスのドメイン名を入力します。
      hosts:
      - rm-xxxx.mysql.rds.aliyuncs.com
      location: MESH_EXTERNAL
      ports:
      # 2. ポートを宣言し、プロトコルを TCP として指定します。
      - name: tcp-mysql
        number: 3306
        protocol: TCP # 重要: プロトコルを TCP として明示的に宣言します。
      # 3. サービス検出に DNS を使用します。
      resolution: DNS

    この ServiceEntry リソースを作成すると、クライアントは外部データベースにアクセスできるようになります。

シナリオ 3: クライアントがメッシュ外にあり、メッシュ内のサーバーが TLS 接続を使用しない場合

サーバーワークロードのポートで mTLS を無効にできます。詳細については、「」および「PeerAuthentication」をご参照ください。

説明

TLS 接続なしでサーバーを直接公開すると、セキュリティリスクが生じる可能性があります。サーバーの TLS 接続を有効にすることをお勧めします。