11

В сервере приложений для разработчиков AppEngine Я получаю сообщение об ошибке, как это:AppEngine UrlFetch validate_certificate = False/Нет не соблюдается

SSLCertificateError: Invalid and/or missing SSL certificate for URL ... 

, когда я делаю выборку, как это на https сервер с самоподписным сертификат (почти всегда localhost пробрасываемых через SSH к виртуальной машине):

result = urlfetch.fetch(url=url, method=method, payload=payload, 
         deadline=DEADLINE, validate_certificate=None) 

не было бы ожидать, SSL отказов для недействительных сертификатов, где validate_certificate является False, хотя это вполне пос возможно, является побочным эффектом политики 2.7.9 в Python, чтобы всегда проверять сертификаты ssl.

Обратите внимание, что проезд False (вместо None) для validate_certificate не работает.

Эта проблема возникает на Python 2.7.9-10 через Homebrew/XCode на OS X 10.10.2-4 с AppEngine с 1.9.18 по 1.19.26.

Об этом в Google App Engine есть проблемы (например, 12096), но я ищу обходное решение.

Вот что я пытался обойти эту проблему:

  1. Добавить сертификат авторизации брелка Мака (работает в браузере, а не от Python)

  2. Добавить сертификат app-engine-python/lib/cacerts/cacerts.txt и/или ./lib/cacerts/urlfetch_cacerts.txt (хотя для этого, вероятно, требуется повернущая поверку на, поскольку это, по-видимому, единственный случай, когда они используются), например

    $ эхо >> /usr/local/share/app-engine-python/lib/cacerts/urlfetch_cacerts.txt

    $ OpenSSL x509 -subject -в server.crt >>/USR/местные /share/app-engine-python/lib/cacerts/urlfetch_cacerts.txt

  3. Отключить SSL HTTPs проверки с PEP-0476 обходного т.е.

    ssl._create_default_https_context = ssl._create_unverified_context

    4444516410 +617451515053691368888

    во время или после import ssl (около линии 1149) от google/appengine/dist27/python_std_lib/httplib.py

Это особенно проблематично, так как на Mac понижение от XCode 7/OS X, Эль капитал больше не является практичным вариантом.

Предпочтительное обходное решение не будет включать в себя обезвреживание кода AppEngine при каждом обновлении сервера приложений разработки.


EDIT

Обратите внимание, что Mac встроенные сертификаты OpenSSL хранятся в /System/Library/OpenSSL, который защищен SIP/rootlessness, который откровенно боль гадость с и стоит функция, чтобы, если мы можем.

Я проверял, что сертификат проверяется с использованием openssl s_client -connect localhost:7500 -CAfile server.pem.

Это было добавлено в брелок и /usr/local/etc/openssl/certs с форматом hash.#, где хэш происходит от openssl x509 -subject_hash -in server.pem (или доморощенного SSL, а именно /usr/local/Cellar/openssl/1.0.2d_1/bin/openssl). В этом случае /usr/local/Cellar/openssl/1.0.2d_1/bin/openssl s_client -connect localhost:7500 проверяет сертификат (но python все еще не работает).

Я пробовал использовать домашнюю версию python и openssl, но безрезультатно. Выполнение следующего в Python, похоже, всегда терпит неудачу;

./pve/bin/python -c "import requests; requests.get('https://localhost:7500')" 

Это также не где SSL_CERT_FILE установлен на сертификат сервера (то есть для дополнительной меры можно было бы ожидать, что она работает, так как команда openssl по существу работает как это), а также не где SSL_CERT_PATH установлен в /usr/local/etc/openssl/certs.

Примечание, pve представляет собой виртуальный окр, где help(ssl) показывает FILE из /usr/local/Cellar/python/2.7.10_2/Frameworks/Python.framework/Versions/2.7/lib/python2.7/ssl.py

Далее проверить, что доморощенный языка Python _ssl.so ссылки на доморощенных-х OpenSSL я побежал:

xcrun otool -L /USR/местные/Cellar /python/2.7.10_2/Frameworks/Python.framework/Versions/2.7/lib/python2.7/lib-dynload/_ssl.so

который возвращает

./Cellar/python/2.7.10_2/Frameworks/Python.framework/Versions/2.7/lib/python2.7/lib-dynload/_ssl.so:

/USR/местные/опт/OpenSSL /lib/libssl.1.0.0.dylib (версия совместимости 1.0.0, текущая версия 1.0.0)

/usr/local/opt/openssl/lib/libcrypto.1.0.0.dylib (версия совместимости 1.0. 0, текущая версия 1.0.0)

/usr/lib/libSystem.B.dylib (совместимость версии 1.0.0, текущая версия 1225.1.1)

Если один работает brew info openssl он замечает под CAVEATS:

Файла CA был бутстрапированным с использованием сертификатов из системы брелки. Для того, чтобы добавить дополнительные сертификаты, поместите .pem файлы в /USR/местные/и т.д./OpenSSL/

сертификаты

но ясно по какой-то причине питона не использует алгоритм OpenSSL доморощенного о возможности поиска сертификатов.

Так я остаюсь в недоумении, почему стандартная библиотека Python не тестирующих сертификатов, которые находятся в каталоге OpenSSL, указанных в документах, а также брелок (в обоих .pem и .p12 форматах, с «всегда доверять» для Secure Sockets Layer (SSL)).

ответ

8

Это ошибка dev_appserver, вызванная изменением поведения httplib.HTTPSConnection (проверка сертификата включена по умолчанию) в недавнем выпуске Python (я верю 2.7.9).

Как ошибка в коде dev_appserver (файл google_appengine/google/appengine/api/urlfetch_stub.py SDK appengine), который запускается независимо от протестированного приложения, нет способа сделать исправление, которое сохранится при обновлении SDK.

Единственный постоянный обходной путь я могу думать будет включить validate_certificate и добавить CA сертификат в файл urlfetch_cacerts.txt. В качестве временного исправления вы можете исправить urlfetch_stub.py с обходным решением №3.

+0

Спасибо @Alex. Невозможно ли добавить сертификат в систему Mac, чтобы использовать Python Httplib? –

+0

Брайан, я не очень хорошо знаком с тем, как python ssl lib работает на Mac, я бы проверил [ssl doc page] (https://docs.python.org/2/library/ssl.html#ssl-contexts) и посмотрите, какая строка пути по умолчанию: 'ssl.get_default_verify_paths()'. Возможно, существует возможность использовать переменную env для установки пути к вашему файлу сертификата (https://www.python.org/dev/peps/pep-0476/#trust-database). – Alex

+0

[Вот соответствующий документ] (http://gagravarr.org/writing/openssl-certs/others.shtml) о том, как добавить самозаверяющий сертификат для openssl. – Alex

1

Я столкнулся с той же проблемой в Windows. Я использовал старую версию Python (2.7). Когда я обновился до Python 2.7.11, проблема исчезла.

Смежные вопросы