Как бороться с сертификатами с помощью Selenium?

Я использую Selenium для запуска браузера. Как я могу работать с веб-страницами (URL), которые попросят браузер принять сертификат или нет?

В Firefox у меня может быть такой веб-сайт, который просит меня принять его сертификат следующим образом:

Fire Fox

В браузере Internet Explorer я могу получить что-то вроде этого:

Введите описание изображения здесь

В Google Chrome:

Гугл Хром

Я повторяю свой вопрос: как я могу автоматизировать принятие сертификата веб-сайта при запуске браузера (Internet Explorer, Firefox и Google Chrome) с Selenium (язык программирования Python)?

20 ответов

Решение

Для Firefox вам нужно установить accept_untrusted_certsFirefoxProfile() возможность True:

from selenium import webdriver

profile = webdriver.FirefoxProfile()
profile.accept_untrusted_certs = True

driver = webdriver.Firefox(firefox_profile=profile)
driver.get('https://cacert.org/')

driver.close()

Для Chrome нужно добавить --ignore-certificate-errorsChromeOptions() аргумент:

from selenium import webdriver

options = webdriver.ChromeOptions()
options.add_argument('--ignore-certificate-errors')

driver = webdriver.Chrome(chrome_options=options)
driver.get('https://cacert.org/')

driver.close()

Для Internet Explorer вам необходимо установить acceptSslCerts желаемая возможность:

from selenium import webdriver

capabilities = webdriver.DesiredCapabilities().INTERNETEXPLORER
capabilities['acceptSslCerts'] = True

driver = webdriver.Ie(capabilities=capabilities)
driver.get('https://cacert.org/')

driver.close()

На самом деле, согласно Desired Capabilities документация, настройка acceptSslCerts способность к True должен работать для всех браузеров, так как это общая возможность чтения / записи:

acceptSslCerts

логический

Должен ли сеанс принимать все сертификаты SSL по умолчанию.


Рабочая демонстрация для Firefox:

>>> from selenium import webdriver

настройка acceptSslCerts в False:

>>> capabilities = webdriver.DesiredCapabilities().FIREFOX
>>> capabilities['acceptSslCerts'] = False
>>> driver = webdriver.Firefox(capabilities=capabilities)
>>> driver.get('https://cacert.org/')
>>> print(driver.title)
Untrusted Connection
>>> driver.close()

настройка acceptSslCerts в True:

>>> capabilities = webdriver.DesiredCapabilities().FIREFOX
>>> capabilities['acceptSslCerts'] = True
>>> driver = webdriver.Firefox(capabilities=capabilities)
>>> driver.get('https://cacert.org/')
>>> print(driver.title)
Welcome to CAcert.org
>>> driver.close()

Для Firefox:

ProfilesIni profile = new ProfilesIni();
FirefoxProfile myprofile = profile.getProfile("default");
myprofile.setAcceptUntrustedCertificates(true);
myprofile.setAssumeUntrustedCertificateIssuer(true);
WebDriver driver = new FirefoxDriver(myprofile);

Для Chrome мы можем использовать:

DesiredCapabilities capabilities = DesiredCapabilities.chrome();
capabilities.setCapability("chrome.switches", Arrays.asList("--ignore-certificate-errors"));
driver = new ChromeDriver(capabilities);

Для Internet Explorer мы можем использовать:

DesiredCapabilities capabilities = new DesiredCapabilities();
capabilities.setCapability(CapabilityType.ACCEPT_SSL_CERTS, true);      
Webdriver driver = new InternetExplorerDriver(capabilities);

Для Firefox Python:

Ошибка самоподписанного сертификата в Firefox теперь исправлена: примите ssl-сертификат с марионеткой firefox webdrive python splinter

"acceptSslCerts" следует заменить на "acceptInsecureCerts"

from selenium import webdriver
from selenium.webdriver.common.desired_capabilities import DesiredCapabilities
from selenium.webdriver.firefox.firefox_binary import FirefoxBinary

caps = DesiredCapabilities.FIREFOX.copy()
caps['acceptInsecureCerts'] = True
ff_binary = FirefoxBinary("path to the Nightly binary")

driver = webdriver.Firefox(firefox_binary=ff_binary, capabilities=caps)
driver.get("https://expired.badssl.com")

И в C# (ядро.net) с помощью Selenium.Webdriver а также Selenium.Chrome.Webdriver как это:

ChromeOptions options = new ChromeOptions();
options.AddArgument("--ignore-certificate-errors");
using (var driver = new ChromeDriver(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location),options))
{ 
  ...
}

Для людей, которые приходят на этот вопрос, связанный с хромом без головы с помощью Python Selen, вам может пригодиться https://bugs.chromium.org/p/chromium/issues/detail?id=721739.

Похоже, вы можете сделать

chrome_options = Options()
chrome_options.add_argument('--allow-insecure-localhost')

или что-то вроде следующего (может потребоваться адаптация для python):

ChromeOptions options = new ChromeOptions()
DesiredCapabilities caps = DesiredCapabilities.chrome()
caps.setCapability(ChromeOptions.CAPABILITY, options)
caps.setCapability("acceptInsecureCerts", true)
WebDriver driver = new ChromeDriver(caps)
    ChromeOptions options = new ChromeOptions().addArguments("--proxy-server=http://" + proxy);
    options.setAcceptInsecureCerts(true);

В Селен Python, вам нужно установить desired_capabilities как:

desired_capabilities = {
    "acceptInsecureCerts": True
}

Javascript:

const capabilities = webdriver.Capabilities.phantomjs();
capabilities.set(webdriver.Capability.ACCEPT_SSL_CERTS, true);
capabilities.set(webdriver.Capability.SECURE_SSL, false);
capabilities.set('phantomjs.cli.args', ['--web-security=no', '--ssl-protocol=any', '--ignore-ssl-errors=yes']);
const driver = new webdriver.Builder().withCapabilities(webdriver.Capabilities.chrome(), capabilities).build();

Я столкнулся с той же проблемой с Selenium и Behat. Если вы хотите передать параметры через behat.ymlвот как это должно выглядеть:

default:
    extensions:
        Behat\MinkExtension:
            base_url: https://my-app.com
            default_session: selenium2
            selenium2:
                browser: firefox
                capabilities:
                    extra_capabilities:
                        acceptInsecureCerts: true

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

from selenium import webdriver

profile = webdriver.FirefoxProfile()
profile.DEFAULT_PREFERENCES['frozen']['marionette.contentListener'] = True
profile.DEFAULT_PREFERENCES['frozen']['network.stricttransportsecurity.preloadlist'] = False
profile.DEFAULT_PREFERENCES['frozen']['security.cert_pinning.enforcement_level'] = 0
profile.set_preference('webdriver_assume_untrusted_issuer', False)
profile.set_preference("browser.download.folderList", 2)
profile.set_preference("browser.download.manager.showWhenStarting", False)
profile.set_preference("browser.download.dir", temp_folder)
profile.set_preference("browser.helperApps.neverAsk.saveToDisk",
                   "text/plain, image/png")
driver = webdriver.Firefox(firefox_profile=profile)
WebDriverManager.chromedriver().setup();
ChromeOptions options = new ChromeOptions();
options.addArguments("--ignore-certificate-errors");
driver = new ChromeDriver(options);

Я использовал его для Java с браузером Chrome, он отлично работает

Создание профиля, а затем драйвера помогает нам обойти проблему с сертификатом в Firefox:

var profile = new FirefoxProfile();
profile.SetPreference("network.automatic-ntlm-auth.trusted-uris","DESIREDURL");
driver = new FirefoxDriver(profile);

У меня была такая же проблема. Однако, когда я попытался открыть веб-сайт вручную в браузере, сертификат был правильным, но в деталях имя было "НЕ ДОВЕРЯТЬ".

Разница в сертификате была вызвана тем, что Fiddler работал в фоновом режиме и расшифровывал весь контент HTTPS перед его повторным шифрованием.

Чтобы решить мою проблему, просто закройте Fiddler на машине. Если вам нужно, чтобы Fiddler оставался открытым, вы можете снять флажок "Расшифровать SSL" в настройках Fiddler.

Простой подход,

      from selenium import webdriver
from selenium.webdriver.chrome.service import Service as ChromeService

# pip install webdriver-manager
from webdriver_manager.chrome import ChromeDriverManager



def get_chrome_capabilities():
    caps = webdriver.DesiredCapabilities.CHROME
    caps['acceptSslCerts'] = True
    caps['acceptInsecureCerts'] = True
    opts = webdriver.ChromeOptions()
    caps.update(opts.to_capabilities())
    return caps


# ChromeDriveManager to automate and download webdriver
service = ChromeService(executable_path=ChromeDriverManager().install())
driver = webdriver.Chrome(
  service=service,
  desired_capabilities=get_chrome_capabilities(),
)

# Use this instead of the above if you are already setup
# driver = webdriver.Chrome(desired_capabilities=get_chrome_capabilities())


driver.get("http://www.google.com")
assert "google" in driver.page_source
driver.quit()

Удалите все, кроме необходимого сертификата, из хранилища сертификатов вашего браузера, а затем настройте браузер на автоматический выбор сертификата при наличии только одного сертификата.

Просто обновление по этой проблеме.

Требуются драйверы:

Linux: Centos 7 64bit, Window 7 64bit

Firefox: 52.0.3

Selenium Webdriver: 3.4.0 (Windows), 3.8.1 (Linux Centos)

GeckoDriver: v0.16.0 (Windows), v0.17.0 (Linux Centos)

Код

System.setProperty("webdriver.gecko.driver", "/home/seleniumproject/geckodrivers/linux/v0.17/geckodriver");

ProfilesIni ini = new ProfilesIni();


// Change the profile name to your own. The profile name can 
// be found under .mozilla folder ~/.mozilla/firefox/profile. 
// See you profile.ini for the default profile name

FirefoxProfile profile = ini.getProfile("default"); 

DesiredCapabilities cap = new DesiredCapabilities();
cap.setAcceptInsecureCerts(true);

FirefoxBinary firefoxBinary = new FirefoxBinary();

GeckoDriverService service =new GeckoDriverService.Builder(firefoxBinary)
    .usingDriverExecutable(new 
File("/home/seleniumproject/geckodrivers/linux/v0.17/geckodriver"))
    .usingAnyFreePort()
    .usingAnyFreePort()
    .build();
try {
    service.start();
} catch (IOException e) {
    e.printStackTrace();
}

FirefoxOptions options = new FirefoxOptions().setBinary(firefoxBinary).setProfile(profile).addCapabilities(cap);

driver = new FirefoxDriver(options);
driver.get("https://www.google.com");

System.out.println("Life Title -> " + driver.getTitle());
driver.close();

Всякий раз, когда я сталкиваюсь с этой проблемой в более новых браузерах, я просто использую AppRobotic Personal edition, чтобы щелкать по конкретным координатам экрана, или нажимать на кнопки и нажимать.

По сути, он просто использует свою макрофункцию, но не будет работать на установках без головы.

Я смог сделать это на.net C# с PhantomJSDriver с веб-драйвером селена 3.1

 [TestMethod]
    public void headless()
    {


        var driverService = PhantomJSDriverService.CreateDefaultService(@"C:\Driver\phantomjs\");
        driverService.SuppressInitialDiagnosticInformation = true;
        driverService.AddArgument("--web-security=no");
        driverService.AddArgument("--ignore-ssl-errors=yes");
        driver = new PhantomJSDriver(driverService);

        driver.Navigate().GoToUrl("XXXXXX.aspx");

        Thread.Sleep(6000);
    }

Для .NET у меня сработало следующее ...

      var chromeOptions = new ChromeOptions { AcceptInsecureCertificates = true };

В значительной степени он сообщает параметрам ChromeDriver не останавливать выполнение браузера при обнаружении небезопасного сертификата и продолжать работу в обычном режиме.

Похоже, что до сих пор нет стандартного решения этой проблемы. Другими словами - вы все еще не можете сказать: "Хорошо, проведите сертификацию, независимо от того, являетесь ли вы Internet Explorer, Mozilla или Google Chrome". Но я нашел один пост, который показывает, как обойти проблему в Mozilla Firefox. Если вы заинтересованы в этом, вы можете проверить это здесь.

Другие вопросы по тегам