質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
86.02%

Q&A

解決済

PerlのLWPでhttps通信が失敗する

pond
pond

総合スコア349

1回答

0グッド

0クリップ

1226閲覧

投稿2022/02/01 08:10

前提・実現したいこと

perlのLWPを用いて、定期実行時のプログラムでhttps通信にてウェブサーバーよりデータを取得しています。
サーバの老朽化に伴い、最近サーバをリプレースしてCentOS6→CentOS7、Perl v5.10.1→v5.16.3へ変わったのですが、
サイトに対するhttps接続が間欠的に失敗するようになりました、下記ソースコードの「#HTTPS通信開始」の箇所で500エラーが帰ってきます。
こちらですが該当の定期実行のプログラムを手動実行するとデータが取得できます。

OSが変わりperlもバージョンアップしてるので、これが影響してるのでしょうか?
(手動でデータが取得できるのが分かりません。)
できるだけプログラムは改修せずに解決できる方法を探しています。

発生している問題・エラーメッセージ

> [2022/01/31 16:02:03] [ERROR] <Access NG>HTTP STATUS=500 Internal Server Error,URL=https://www.example.com/example/example.aspx > HTTP/1.1 500 Internal Server Error > Cache-Control: private > Date: Mon, 31 Jan 2022 07:02:02 GMT > Server: Microsoft-IIS/8.5 > Content-Type: text/html > Client-Date: Mon, 31 Jan 2022 07:02:03 GMT > Client-Peer: 202.214.225.112:443 > Client-Response-Num: 1 > Client-SSL-Cert-Issuer: /C=JP/O=Cybertrust Japan Co., Ltd./CN=Cybertrust Japan SureServer CA G4 > Client-SSL-Cert-Subject: /C=JP/ST=Tokyo/L=example-ku/O=NIHONJUTAKUHOSHOKENSAKIKO, KK/OU=Information Systems/CN=www.example.com > Client-SSL-Cipher: ECDHE-RSA-AES128-GCM-SHA256 > Client-SSL-Socket-Class: IO::Socket::SSL > Client-SSL-Version: TLSv1_2 > Client-Transfer-Encoding: chunked > Set-Cookie: ASP.NET_SessionId=430u4t55edfrz1yhzepevk45; path=/; HttpOnly > Set-Cookie: BIGipServerPool_pr-p2pri-oap01-2=86056970.20480.0000; path=/; Httponly; Secure > Title: 500 -内部サーバー エラーです。 > X-AspNet-Version: 2.0.50727 > X-Powered-By: ASP.NET > > <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> > <html xmlns="http://www.w3.org/1999/xhtml"> > <head> > <meta http-equiv="Content-Type" content="text/html; charset=shift_jis"/> > <title>500 -内部サーバー エラーです。</title> > <style type="text/css">

該当のソースコード

perl

1#!/usr/bin/perl 2 3use strict; 4use warnings; 5use Config::Tiny; 6use DBI; 7use HTTP::Request::Common; 8use LWP::UserAgent; 9use Mozilla::CA; 10use Time::Piece; 11use Time::Seconds; 12 13#####設定ファイルの読み込み######### 14print "IniFile Read\n"; 15 16#コンフィグの作成(&OPEN) 17my $config = Config::Tiny->new->read("/test/ini/example.ini") or die(qq/Can't open file "example.ini": $!/); 18#実行レベルの取得 19my $level = $config->{_}; 20 21#CSV取得タイムフラグ 22my $time_chk = $level->{"time_chk"}; 23my $get_csv_span = $level->{"get_csv_span"}; 24my $csv_header = $level->{"csv_header"}; 25 26#ログ 27my $log_msg = $level->{"log_msg"}; 28my $log_file = $level->{"log_file"}; 29my $err_file = $level->{"err_file"}; 30 31#バックアップ 32my $backup_path = $level->{"backup_path"}; 33my $backup_file = $backup_path."csv.log"; 34 35#通信 36#my $proxy = $level->{"proxy"}; 37my $base_url = $level->{"base_url"}; 38my $login_url = $level->{"login_url"};; 39my $login_user = $level->{"login_user"}; 40my $login_pass = $level->{"login_pass"}; 41my $csv_url = $level->{"csv_url"}; 42my $logout_url = $level->{"logout_url"}; 43 44#CSV 45my $get_csvpath = $level->{"get_csvpath"}; 46my $set_csvpath = $level->{"set_csvpath"}; 47my $bak_csvpath = $level->{"bak_csvpath"}; 48my $add_role = $level->{"add_role"}; 49 50#Import 51my $import_flag = $level->{"import_flag"}; 52my $import_exec = $level->{"import_exec"}; 53 54#データベース 55my $db_connect = $level->{"db_connect"}; 56my $username = $level->{"username"}; 57my $password = $level->{"password"}; 58 59#######変数宣言######## 60 61#ログ出力 62my $fh_log; 63my @log_data; 64 65#通信系 66my $url; 67my $req; 68my $res; 69my $cookie; 70 71#データベース 72my $sql; 73my @data; 74 75####################### 76 77#スタート 78print "CSV_BATCH START\n"; 79 80$log_msg = "CSV_BATCH START"; 81log_output(); 82 83#UpdateTime取得 84$sql = "select update_time from batch_history;"; 85@data = db_execute($sql); 86 87#更新日時をdate型で取得 88my $dt_fr = get_dt($data[0]); 89my $dt_to = set_date($dt_fr,$get_csv_span); 90 91print "dt_fr=>".$dt_fr."\n"; 92print "dt_to=>".$dt_to."\n"; 93 94 95#取得時間ズレチェック 96if ($time_chk){ 97 98 # fr < to < real = OK 99 if ( set_date(time,0) - $dt_fr < 0 or set_date(time,0) - $dt_to < 0){ 100 101 my $log = "<Get Time Is Wrong>"; 102 $log .= "FROM:".$dt_fr." < ". "TO:".$dt_to." < NOW:".localtime(time); 103 err_log_set($log); 104 exit 1; 105 } 106} 107 108#HTTPS通信開始 109my $ua = LWP::UserAgent->new; 110#HTTPS通信設定(connectメソッドを使用) 111#$ua->proxy("https", "connect://".$proxy); 112#CA認証許可設定 113#$ua->ssl_opts(verify_hostname => 0); #ホストの検証なし 114$ua->ssl_opts (SSL_ca_file => Mozilla::CA::SSL_ca_file()); #CA認証を呈示 115#タイムアウト設定 116#$ua->timeout( "10" ); 117 118print "Access1 execute!\n"; 119 120#POSTパラメータ作成 121my %postdata = ( "user" => $login_user, "pass" => $login_pass ); 122#POST送信 123$url = $base_url.$login_url; 124$req = POST( $url, [\%postdata] ); 125$res = $ua -> request( $req ); 126 127#アクセス確認(200 OK) 128if ($res->is_success) { 129 130 my $id = ""; 131 print "Access1 success\n"; 132 133 eval { 134 135 #Cookieの取得 136 my @cook = $res->header('Set-Cookie'); 137 $cook[0] =~ s/;.*?$//; 138 $cook[1] =~ s/;.*?$//; 139 $cookie = $cook[0].";".$cook[1]; 140 141 #GETパラメータの作成 142 $id = $res->content; 143 my $P1 = get_dt_str($dt_fr,"%04d/%02d/%02d"); 144 my $P2 = sprintf("%02d", $dt_fr->hour); 145 my $P3 = sprintf("%02d", $dt_to->hour); 146 147 #GET送信 148 print "Access2 execute!\n"; 149 $url = $base_url.$csv_url."?ID=".$id."&P1=".$P1."&P2=".$P2."&P3=".$P3; 150 $req = HTTP::Request->new( 'GET', $url ); 151 $req->header( "cookie" => $cookie ); 152 $res = $ua->request( $req, $get_csvpath ); 153 #$res = $ua->request( $req ); 154 155 #アクセス確認(200 OK) 156 if ($res->is_success) { 157 158 #成功 159 print "Access2 success\n"; 160 161 #ログアウト 162 print "Access3 execute!\n"; 163 164 #GETパラメータ作成 165 $url = $base_url.$logout_url."?ID=".$id; 166 #GET送信 167 $req = HTTP::Request->new( 'GET', $url ); 168 $req->header( "cookie" => $cookie ); 169 $res = $ua->request( $req ); 170 171 #アクセス確認(200 OK) 172 if($res->is_success){ 173 174 print "Access3 success\n"; 175 }else{ 176 #失敗 177 print "Access3 fails\n"; 178 access_err_set(); 179 exit 1; 180 } 181 }else{ 182 #失敗 183 print "Access2 fails\n"; 184 access_err_set(); 185 exit 1; 186 } 187 #サーバとのHTTPS通信終了 188以下、省略

試したこと

該当の定期実行のプログラムを手動実行するとデータが取得できます。

補足情報(FW/ツールのバージョンなど)

● 新しいサーバ
CentOS Linux release 7.9.2009 (Core)
Perl v5.16.3
↓データ取得時に使用してるモジュール
Time::Piece 1.20_01
DBI 1.643
LWP::UserAgent 1.9601
HTTP::Request::Common 6.36
Mozilla::CA 20211001
LWP::Protocol::connect 6.09
Config::Tiny 2.14
Crypt::SSLeay 0.64
IO::Socket::SSL 2.074

● 古いサーバ
CentOS release 6.10 (Final)
Perl v5.10.1
↓データ取得時に使用してるモジュール
Time::Piece 1.24
DBI 1.630
LWP::UserAgent 1.00
HTTP::Request::Common 6.04
Mozilla::CA 20130114
LWP::Protocol::connect 6.06
Config::Tiny 2.20
Crypt::SSLeay 0.64
IO::Socket::SSL 1.962

以下のような質問にはグッドを送りましょう

  • 質問内容が明確
  • 自分も答えを知りたい
  • 質問者以外のユーザにも役立つ

グッドが多くついた質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

気になる質問をクリップする

クリップした質問は、後からいつでもマイページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

下記のような質問は推奨されていません。

  • 間違っている
  • 質問になっていない投稿
  • スパムや攻撃的な表現を用いた投稿

適切な質問に修正を依頼しましょう。

回答1

0

自己解決

データ取得先のサーバでCRONでデータを取得しに行くときに、ファイルが完全に生成されてなかったり(文字コードがunknown-8bitになってる)、
ネットワークに負荷がかかってたりするとこのような事象起きるようです。
定期実行時間を5分ずらしたら正常に取得できるようになりました。お騒がせしました。
500エラーは要因が様々なので、調べるのに時間が掛かってしまいました。

投稿2022/02/04 02:33

pond

総合スコア349

良いと思った回答にはグッドを送りましょう。
グッドが多くついた回答ほどページの上位に表示されるので、他の人が素晴らしい回答を見つけやすくなります。

下記のような回答は推奨されていません。

  • 間違っている回答
  • 質問の回答になっていない投稿
  • スパムや攻撃的な表現を用いた投稿

このような回答には修正を依頼しましょう。

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
86.02%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問

同じタグがついた質問を見る