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 8.0.11 MSI バージョンのインストールと構成のグラフィック チュートリアル

この記事では、MySQL 8.0.11 MSIバージョンのインストールと設定のチュートリアルを参考ま...

JavaScript の組み込みオブジェクト 数学と文字列の詳細な説明

目次数学オブジェクト共通プロパティ一般的な方法Math.random()文字列メソッド長さプロパティ...

MySQLのレプリケーションとチューニングの原則と方法を分析する

1. はじめにMySQL にはレプリケーション ソリューションが付属しており、次のような利点がありま...

Vue で Alibaba のアイコンフォント ベクター アイコンを使用する方法について

インターネット上には多くのインポート方法があり、公式も3つのインポート方法を提供していますが、インポ...

Nginx 最適化サービスで Web ページ圧縮を実装する方法

リソースを節約するためにWebページの圧縮を設定する1.まず、設定を変更しましょう vim /usr...

MySQL で CURRENT_TIMESTAMP を使用する方法

目次CURRENT_TIMESTAMPの使用CURRENT_TIMESTAMPを使用したタイムスタン...

クラウド CentOS で Docker リモート サービス リンクを有効にするための実装手順

ここでは、dockerがインストールされたcentosサーバーを紹介し、リモートリンクサービスを開始...

MySQL カウントを向上させる方法のまとめ

多くのプログラマーは MySQL に精通していると思います。多くの人が count の使い方と、最適...

node.jsのコアモジュールとは

目次グローバルオブジェクトグローバルオブジェクトとグローバル変数プロセスコンソール一般的なツールユー...

1つの記事でJavaScript DOM操作の基本を学ぶ

DOM の概念DOM: ドキュメント オブジェクト モデル: ドキュメント オブジェクト モデルは、...

MySQL のインデックスとデータ テーブルを管理する方法

目次テーブルの競合を見つけて修正するインデックス統計の更新テーブルの競合を見つけて修正するデータ テ...

回転するフリップカードアニメーションの効果を実現するCSS

回転フリップ効果の CSS アニメーション、具体的な内容は次のとおりです。 1. まず2つのボックス...

Vue2.0+ElementUI+PageHelperで実装されたテーブルページング機能

序文最近、いくつかのフロントエンド プロジェクトに取り組んでおり、ページにいくつかのテーブルを表示す...

Docker+Jenkinsによる自動デプロイの実現方法

Code Cloud を使用して Git コード ストレージ ウェアハウスを構築するhttps://...