MySQL データベース接続例外の概要 (収集する価値あり)

MySQL データベース接続例外の概要 (収集する価値あり)

Centos にプロジェクトをデプロイするときに奇妙な問題が見つかりました。データベース接続で例外が繰り返し発生していました。そこで私は 2 時間かけてデータベース接続異常のさまざまな原因を探し、ようやく問題は解決しました。同時に、解決プロセス中に収集された異常な情報を要約して、同様の問題に遭遇したときにアイデアを提供します。必需品です。

問題現象

まず最初に私が遭遇した問題についてお話しします。プロジェクトで発生した問題は非常に奇妙です。Mysql データベースは Centos にインストールされており、プロジェクトでは Spring Boot を使用しています。

プロジェクトはローカルで起動し、通常どおりサーバー データベースに接続し、ローカル データベース クライアントは通常どおりサーバー データベースに接続し、サーバー ローカル接続クライアントは通常どおりデータベースに接続します。スローされる唯一の例外は、プロジェクトがサーバーにデプロイされ、開始されたときです。

例外情報は次のとおりです(その時点では例外情報は保持されていませんでした)。

com.mysql.jdbc.exceptions.jdbc4.CommunicationsException: 通信リンク障害

最後にパケットがサーバーに正常に送信されたのは 0 ミリ秒前です。ドライバーはサーバーからパケットを受信して​​いません。
sun.reflect.NativeConstructorAccessorImpl.newInstance0(ネイティブ メソッド)
sun.reflect.NativeConstructorAccessorImpl.newInstance(ソース不明)
sun.reflect.DelegatingConstructorAccessorImpl.newInstance(不明なソース)
java.lang.reflect.Constructor.newInstance(ソース不明)
com.mysql.jdbc.Util.handleNewInstance(Util.java:425) で
com.mysql.jdbc.SQLError.createCommunicationsException(SQLError.java:989) で
com.mysql.jdbc.MysqlIO.<init>(MysqlIO.java:341) で
com.mysql.jdbc.ConnectionImpl.coreConnect(ConnectionImpl.java:2196) で
com.mysql.jdbc.ConnectionImpl.connectOneTryOnly(ConnectionImpl.java:2229) で
com.mysql.jdbc.ConnectionImpl.createNewIO(ConnectionImpl.java:2024) で
com.mysql.jdbc.ConnectionImpl.<init>(ConnectionImpl.java:779) で
com.mysql.jdbc.JDBC4Connection.<init>(JDBC4Connection.java:47) で
sun.reflect.NativeConstructorAccessorImpl.newInstance0(ネイティブ メソッド)
sun.reflect.NativeConstructorAccessorImpl.newInstance(ソース不明)
sun.reflect.DelegatingConstructorAccessorImpl.newInstance(不明なソース)
java.lang.reflect.Constructor.newInstance(ソース不明)
com.mysql.jdbc.Util.handleNewInstance(Util.java:425) で
com.mysql.jdbc.ConnectionImpl.getInstance(ConnectionImpl.java:389) で
com.mysql.jdbc.NonRegisteringDriver.connect(NonRegisteringDriver.java:330) で
java.sql.DriverManager.getConnection(不明なソース)
java.sql.DriverManager.getConnection(不明なソース)
com.ad.MysqlDemo.main(MysqlDemo.java:32) で
原因: java.net.ConnectException: 接続が拒否されました: connect
java.net.DualStackPlainSocketImpl.connect0(ネイティブメソッド)
java.net.DualStackPlainSocketImpl.socketConnect(ソース不明)
java.net.AbstractPlainSocketImpl.doConnect(ソース不明)
java.net.AbstractPlainSocketImpl.connectToAddress(不明なソース)
java.net.AbstractPlainSocketImpl.connect(ソース不明)
java.net.PlainSocketImpl.connect(ソース不明)
java.net.SocksSocketImpl.connect(ソース不明)
java.net.Socket.connect(不明なソース)
com.mysql.jdbc.StandardSocketFactory.connect(StandardSocketFactory.java:211) で
com.mysql.jdbc.MysqlIO.<init>(MysqlIO.java:300) で
... 15件以上

異常な原因

インターネット上のほぼすべての解決策を試しましたが、効果はありませんでした。次第に、JDK に原因があるのではないかと疑い始めました。ローカルで使用されている JDK バージョンは 1.8.0_151 で、サーバーでは 1.8.0.242 が使用されています。理論的には影響はありません。

そこで、サーバー上のjdkをアンインストールし、公式サイトからインストールパッケージをダウンロードして、1.8.0_241を再インストールしました。データベース接続の問題は解消されました。

後でよく考えてみると、マイナーバージョン番号の問題ではなく、インストールされている JDK バージョンの問題であることがわかりました。このマシンにインストールされている JDK は、Oracle 公式サイトからダウンロードし、サーバー上のストレージは便宜上 yum コマンドを使用して直接インストールしました。 OpenJDK は CentOS にデフォルトでインストールされます。 jdk7 以降、JDK と OpenJDK はライセンス契約が異なる 2 つのバージョンに属し、OpenJDK ソース コードは不完全であり、OpenIDK には最も合理化された JDK のみが含まれていることがわかっています。

以下では、上記の例外を検索中に見つかった、同様の例外につながるその他の理由とその解決策を紹介します。

ソックパス問題

問題現象は上記と同じです。サーバーにデプロイされたアプリケーションがサーバーに接続できないことを除いて、他の方法ではデータベースに接続できます。

問題の原因は、サーバーに 2 つのディスクがあり、データベースのストレージ コンテンツを移動するために途中で mv コマンドが実行され、同時に datadir が新しいディレクトリを指すように変更されたことです。

結果: JAVA プログラムを使用したローカル接続が失敗し、org.apache.commons.dbcp.SQLNestedException: PoolableConnectionFactory を作成できません (通信リンク障害例外がスローされました。

解決策: 対応する datadir 設定を変更した後、mysql.sock ファイル パスの構成を確認します。デフォルトでは、/var/lib/mysql/mysql.sock または /temp/mysql.sock にあります。次に、すべてのターミナル ([client]、[mysql]、[mysqld] など) が同じパスを使用するように変更します。

SSL接続の問題

メッセージに次の異常な情報が表示された場合:

javax.net.ssl.SSLHandshakeException: 適切なプロトコルがありません (プロトコルが無効になっているか、暗号スイートが不適切です)
sun.security.ssl.Handshaker.activate(Handshaker.java:529) で
sun.security.ssl.SSLSocketImpl.kickstartHandshake(SSLSocketImpl.java:1492) で
sun.security.ssl.SSLSocketImpl.performInitialHandshake(SSLSocketImpl.java:1361) で
sun.security.ssl.SSLSocketImpl.startHandshake(SSLSocketImpl.java:1413) で
sun.security.ssl.SSLSocketImpl.startHandshake(SSLSocketImpl.java:1397) で

SSL 接続に問題がある可能性があります。インターネット上の友人が、jdk1.8 にアップグレードした後に上記の例外に遭遇しました。

解決策: SSLv3 を削除します。 JAVA_HOME/jre/lib/security/java.security ファイルで jdk.tls.disabledAlgorithns=SSLv3,... に関連する構成を見つけて、SSLv3 の部分を削除します。 SSLv3 を削除すると SSL 呼び出しが可能になります。

SSL 接続の問題に関しては、Mysql が SSL 接続を使用する別の状況があります。設定方法については、こちらの記事を参照してください:https://www.jb51.net/article/100432.htm。

データベース接続タイムアウト

この状況はインターネット上の主流の情報であり、多数の記事がありますが、多くの場合、具体的なシナリオは説明されていません。アプリケーションの使用中に上記と同様の例外が発生します。これは起動時ではなく、使用中であることに注意してください。

使用中に例外が発生する理由は、MySQL サーバーのデフォルトの「wait_timeout」が 8 時間 (28800 秒) であるためです。つまり、接続が 8 時間以上アイドル状態 (非アクティブ) になると、MySQL は自動的に接続を切断します。ただし、接続プールは接続がまだ有効であると信じています (接続の有効性が検証されていないため)。アプリケーションが接続の使用を申請すると、上記のエラーが発生します。

解決策: my.ini 設定を変更し、タイムアウト期間を長くするか、接続 URL に「&autoReconnect=true」を追加します。

port=3306 の下に次の構成を追加します。

待機タイムアウト=31536000
インタラクティブタイムアウト=31536000

次に、MySQL を再起動します。

この状況は、データベース接続プールの maxIdleTime 構成によっても発生する可能性があります。

<!-- 最大アイドル時間。60 秒以内に使用されない場合、接続は破棄されます。 0 の場合は破棄されません。デフォルト: 0 -->  
<プロパティ名="maxIdleTime" 値="0"></プロパティ>

MySQL 接続は 8 時間以上アイドル状態になると閉じられますが、接続プールは接続を破棄せず、接続を有効と見なすため (接続の有効性が検証されないため)、アプリケーションが接続の使用を申請すると、上記のエラーが発生します。

解決策: 値を 20 に設定します。

その他の原因

もちろん、MySQL 接続で同様の例外が発生する理由は他にもたくさんあります。

  • データベース アカウントのアクセス権の問題: IP とアカウントの承認を指定します。
  • ネットワーク権限の問題: ファイアウォールは対応するアクセス権限で有効になっていますか?
  • ポートの問題: アクセスしたポートは正しいですか? ポートでファイアウォールの許可が有効になっていますか?
  • アカウント パスワードの問題: アカウント パスワードが間違っているか、アカウントに指定された IP アドレスへのアクセス権がありません。
  • データベース ドライバーの問題: データベース ドライバーのバージョンがデータベースのバージョンと一致しません。
  • ネットワークの安定性の問題: 不安定なネットワークによって発生する問題。
  • データベース接続プールの問題: データベース接続プールの設定が大きすぎるため、デフォルトの MySQL 接続が不足しています。
  • IPv4 と IPv6 の問題。

上記は、MySQL データベース接続例外の詳細な概要です。MySQL データベース接続例外の詳細については、123WORDPRESS.COM の他の関連記事に注目してください。

以下もご興味があるかもしれません:
  • IDEA を使用して Tomcat を設定し、MySQL データベース (JDBC) に接続するための詳細な手順
  • Navicat Premium がデータベースに接続すると、次のエラー メッセージが表示されます: 2003 ''localhost'' の MySQL サーバーに接続できません (10061)
  • IntelliJ IDEA で Java を使用して MySQL データベースに接続する方法の詳細な説明
  • AndroidはMySQLデータベースに接続し、追加、削除、変更、クエリ操作を実行します。
  • Node-Redを使用してMySQLデータベースに接続する方法

<<:  Centos7 への MySQL8 のインストールチュートリアル

>>:  シンプルなドラッグ効果を実現するJavaScript

推薦する

MySql のクラッシュとサービスの起動失敗の解決策

私は長い間PHPに触れてきましたが、インストール環境は非常に不慣れです。多くの問題に遭遇しました。B...

react-color を使用してフロントエンドのカラーピッカーを実装する方法

背景次の図に示すように、 react-color を使用してフロントエンド インターフェースのカラー...

ウェブページのカラーマッチングにおけるオーバーラップとソフトカラーマッチングの手法を詳しく説明

この記事には、細かい点は一切なく、カラーマッチングのテクニックをシェアするだけです。とてもシンプルで...

MySQL ストアド プロシージャの使用例の分析

この記事では、MySQL ストアド プロシージャの使用方法について説明します。ご参考までに、詳細は以...

Javascript で SessionStorage と LocalStorage を使用する方法

目次序文SessionStorage と LocalStorage の紹介SessionStorag...

Node.jsで子プロセスを作成する方法

目次導入子プロセスプロセスを非同期的に作成する同期作成プロセス導入Node.js のメイン イベント...

psdカット画像をdiv+css形式に変換する

PSD から div css へのウェブページ切り取り例ステップ 1: まず、すべてのタグの内側と外...

Vue要素ツリーコントロールに点線を追加する詳細な説明

目次1. 成果を達成する2. 実装コード3. その他の実装要約する1. 成果を達成する 2. 実装コ...

MySQLクエリの基本的なクエリ操作の学習

序文MySQL は最も人気のあるリレーショナル データベース管理システムです。WEB アプリケーショ...

ウェブサイトアイコンを追加するにはどうすればいいですか?

最初のステップは、アイコン作成ソフトウェアを準備することです。まず、いわゆるアイコンは拡張子 .ic...

docker を使用して Kong クラスター操作を構築する

docker コンテナの下に kong クラスターを構築するのは非常に簡単です。公式サイトの紹介も非...

ubuntu15.10 での hadoop2.7.2 の詳細なインストールと設定

Linux での Hadoop インストール チュートリアルはインターネットや書籍に多数ありますが、...

divは、自動入力スタイルをブロックする入力ボックスとして入力を使用せずにコンテンツを入力できます。

今日、私は公開用の動的なウィンドウ スタイルを設計しましたが、マウスで入力をクリックしたときにブラウ...

MySQLデータベースでサポートされているストレージエンジンの比較

目次ストレージエンジンMySQL でサポートされているストレージ エンジン同時実行制御ロック粒子をロ...

Windows で MySQL 5.6 を 5.7 にアップグレードする方法

前面に書かれたMySQL をアップグレードする方法には、インプレース アップグレードと論理アップグレ...