Reputation: 20163
I installed python 3.6 using
brew install python3
and tried to download a file with six.moves.urllib.request.urlretrieve
from an https, but it throws the error
ssl.SSLError: [SSL: CERTIFICATE_VERIFY_FAILED] certificate verify failed (_ssl.c:749)
In the Python installation (from .pkg), the README indicates that one needs to run the Install Certificates.command
after the installation to
certifi
certify
pathto be able to use certificates.
However, in brew install, this file does not exist and it does not seem to be run.
Upvotes: 50
Views: 109552
Reputation: 1
I did a combination of two of the above answers:
I ran:
python3 -c 'import ssl; print(ssl.get_default_verify_paths().openssl_cafile)'
to get where Python thought the cert.pem file should be and there was nothing there. For me it was /Library/Frameworks/Python.framework/Versions/3.10/etc/openssl/cert.pem but I expect others installations to be different.
I ran:
ls /private/etc/ssl/
Which showed that there was a cert.pem there.
I changed directory to where Python openssl looked for the cert.pem file. For me that was:
cd /Library/Frameworks/Python.framework/Versions/3.10/etc/openssl/
Then I created a link from the one in /private to the openssl directory:
ln -s /private/etc/ssl/cert.pem cert.pem
After that, the error went away.
Upvotes: 0
Reputation: 1
I had the same issue with Python 3.11. I went to the Python directory and did the following steps. I did the first step because the terminal did not have the permission to do this action.
After these two steps, my application is executable!
Upvotes: 0
Reputation: 41
You will not be able to find this file in Application -> Python folder.
On MAC Press Command + Space to open Spotlight Search and type 'Install Certificates.command', then execute it. This solution resolved the issue for me.
Upvotes: 3
Reputation: 3603
positionning SSL_CERT_FILE env var to your ca file also works and it is not invasive.
Upvotes: 1
Reputation: 889
If you need to make your local root certificate (e.g. local_RootCA.crt
) become trusted by python, you can add it into the end of certifi/cacert.pem
file:
cat local_RootCA.crt >> `python -c 'import certifi; print(certifi.where())'`
That solution works good for macos brew python 3 installation as well.
Upvotes: 9
Reputation: 177
For temporary, following will disable the ssl checking,
import ssl
ssl._create_default_https_context = ssl._create_unverified_context
Upvotes: 12
Reputation: 1260
python -c 'import ssl; print(ssl.get_default_verify_paths().openssl_cafile)'
/Applications/Xcode.app/Contents/Developer/Library/Frameworks/Python3.framework/Versions/3.7/etc/ssl/cert.pem
sudo mkdir -p /Applications/Xcode.app/Contents/Developer/Library/Frameworks/Python3.framework/Versions/3.7/etc/ssl/certs
certifi
python -c 'import certifi; print(certifi.where())'
'/usr/local/lib/python3.7/site-packages/certifi/cacert.pem'
sudo cp /usr/local/lib/python3.7/site-packages/certifi/cacert.pem
/Applications/Xcode.app/Contents/Developer/Library/Frameworks/Python3.framework/Versions/3.7/etc/ssl/certs/cert.pem
Upvotes: 26
Reputation: 3738
My solution for Mac OS X:
1) Upgrade to Python 3.6.5 using the native app Python installer downloaded from the official Python language website https://www.python.org/downloads/
I've found that this installer is taking care of updating the links and symlinks for the new Python a lot better than homebrew.
2) Install a new certificate using "./Install Certificates.command" which is in the refreshed Python 3.6 directory
cd "/Applications/Python 3.6/" sudo "./Install Certificates.command"
Upvotes: 37
Reputation: 20163
It seems that, for some reason, Brew has not run the Install Certificates.command
that comes in the Python3 bundle for Mac. The solution to this issue is to run the following script (copied from Install Certificates.command
) after brew install python3
:
# install_certifi.py
#
# sample script to install or update a set of default Root Certificates
# for the ssl module. Uses the certificates provided by the certifi package:
# https://pypi.python.org/pypi/certifi
import os
import os.path
import ssl
import stat
import subprocess
import sys
STAT_0o775 = ( stat.S_IRUSR | stat.S_IWUSR | stat.S_IXUSR
| stat.S_IRGRP | stat.S_IWGRP | stat.S_IXGRP
| stat.S_IROTH | stat.S_IXOTH )
def main():
openssl_dir, openssl_cafile = os.path.split(
ssl.get_default_verify_paths().openssl_cafile)
print(" -- pip install --upgrade certifi")
subprocess.check_call([sys.executable,
"-E", "-s", "-m", "pip", "install", "--upgrade", "certifi"])
import certifi
# change working directory to the default SSL directory
os.chdir(openssl_dir)
relpath_to_certifi_cafile = os.path.relpath(certifi.where())
print(" -- removing any existing file or link")
try:
os.remove(openssl_cafile)
except FileNotFoundError:
pass
print(" -- creating symlink to certifi certificate bundle")
os.symlink(relpath_to_certifi_cafile, openssl_cafile)
print(" -- setting permissions")
os.chmod(openssl_cafile, STAT_0o775)
print(" -- update complete")
if __name__ == '__main__':
main()
Upvotes: 162