Сценарии сломались после обновления LWP "сертификат не удался"

У меня много сценариев, большинство из которых основаны на WWW::Mechanize которые очищают данные от разного оборудования, доступного через HTTP. После обновления большей части моей установки Perl и ее модулей все сценарии, использующие HTTPS:// сломались из-за "certificate verify failed"

Это является результатом того факта, что более новые версии LWP правильно проверяют сертификат и dies если что-то не совпадает

В моем случае из-за обстоятельств ожидается сбой проверки подлинности сертификата, поэтому мне нужно было найти способ аккуратно обойти эту проверку.

5 ответов

Решение

Сначала я добавил свой код:

system("export PERL_LWP_SSL_VERIFY_HOSTNAME=0");

... но так как это неоптимально (так как это затрагивает в основном весь сеанс входа в систему).
Редактировать: Кроме того, экспорт таким образом ничего не делает, так как я исказил мою логику. Смотрите комментарии ниже.

Затем я изменил его, добавив код:

$ENV{'PERL_LWP_SSL_VERIFY_HOSTNAME'} = 0;

И после этого только сценарии, которые должны обойти проверку, делают это простым и понятным способом.

Скажи, что я хочу сказать тебе кое-что, и я не хочу, чтобы кто-то еще знал это. Мы договорились бы о пароле, и я бы использовал его для шифрования сообщения, а затем отправил бы вам сообщение.

Что если я не позабочусь о том, чтобы человеком, которому я дал пароль и зашифрованное сообщение, был ты? Тогда любое количество людей может просто выдать себя за вас, и шифрование будет напрасным. Это было состояние поддержки HTTPS LWP до недавнего времени.

Теперь LWP на самом деле проверяет, с кем он разговаривает, если вы не попросите LWP вести себя так, как когда-то. Вы можете сделать это используя:

my $ua = LWP::UserAgent->new(
   ssl_opts => { verify_hostname => 0 },
);

Если вы хотите повлиять на все экземпляры LWP::UserAgent в вашем скрипте, не указав опцию повсеместно, вы можете добавить следующее в ваш скрипт

$ENV{PERL_LWP_SSL_VERIFY_HOSTNAME} = 0;

Или вы можете запустить свой скрипт следующим образом:

PERL_LWP_SSL_VERIFY_HOSTNAME=0 script.pl

Наконец, если вы хотите, чтобы LWP всегда был небезопасным, вы можете добавить следующее в ваш скрипт входа в систему:

export PERL_LWP_SSL_VERIFY_HOSTNAME=0

Однако я не рекомендую ничего из вышеперечисленного. Гораздо лучшим вариантом будет предоставить сертификат для хоста, с которым вы общаетесь. (Это эквивалентно добавлению исключения в Firefox, если вы знаете, что я имею в виду.) См. Документацию для $ua->ssl_opts,

Для меня, используя:

my $ua = LWP::UserAgent->new(
  ssl_opts => { verify_hostname => 0 },
);

Поддавшись

Использование по умолчанию SSL_verify_mode SSL_VERIFY_NONE для клиента не рекомендуется! Пожалуйста, установите SSL_verify_mode на SSL_VERIFY_PEER вместе с SSL_ca_file|SSL_ca_path для проверки. Если вы действительно не хотите проверять сертификат и держать соединение открытым для атак типа "человек-посредник", пожалуйста, явно задайте для SSL_verify_mode значение SSL_VERIFY_NONE в вашем приложении.

Использование этого не дало никаких предупреждений:

my $ua = LWP::UserAgent->new(
  ssl_opts => { SSL_verify_mode => 'SSL_VERIFY_NONE'},
);

@ikegami дает хороший аргумент, почему вы не хотите отключать проверку имени хоста SSL, но прямо не упоминает, как этого избежать.

Если вы говорите с общедоступной системой с сертификатом, подписанным CA, вам нужно указать LWP на коллекцию корневых сертификатов вашего дистрибутива. В системе на основе Debian (Ubuntu и т. Д.) Это хранится в /etc/ssl/certs/,

BEGIN {
    $ENV{HTTPS_CA_DIR} = '/etc/ssl/certs'
}

Если вы говорите со своим собственным сервером с самозаверяющим сертификатом, вы можете сохранить копию этого сертификата на клиенте и указать свой сценарий на этот конкретный файл.

BEGIN {
    $ENV{HTTPS_CA_FILE} = '/path/to/my/server-certificate.crt'
}

Вместо этого вы можете установить их в среде перед запуском скрипта (например, экспортировать их из вашей оболочки) или применить параметры непосредственно к объекту UserAgent. См. Документацию LWP::UserAgent для более подробной информации; ищи ssl_opts (примерно на полпути вниз по странице).

Добавьте библиотеку вверху и добавьте остальные объявления ENV и информацию о сокетах ввода-вывода перед использованием функций модуля LWP. Тогда попробуйте, это будет тренировка.

      use IO::Socket::SSL;
use LWP::UserAgent;

$ENV{'PERL_LWP_SSL_VERIFY_HOSTNAME'} = 0;
$ENV{HTTPS_DEBUG} = 1;
        
IO::Socket::SSL::set_ctx_defaults(
  SSL_verifycn_scheme => 'www',
  SSL_verify_mode => 0,
);

$ua = LWP::UserAgent->new();
Другие вопросы по тегам