discord.py: SSLCertVerificationError: certificate has expired
Today suddenly my bot can’t be launched from Windows. As I see this problem is not in my code completely so I messaging here and to Discord Support.
Traceback (most recent call last):
File "...\lib\site-packages\aiohttp\connector.py", line 936, in _wrap_create_connection
return await self._loop.create_connection(*args, **kwargs) # type: ignore # noqa
File "...\lib\asyncio\base_events.py", line 1050, in create_connection
transport, protocol = await self._create_connection_transport(
File "...\lib\asyncio\base_events.py", line 1080, in _create_connection_transport
await waiter
File "...\lib\asyncio\sslproto.py", line 529, in data_received
ssldata, appdata = self._sslpipe.feed_ssldata(data)
File "...\lib\asyncio\sslproto.py", line 189, in feed_ssldata
self._sslobj.do_handshake()
File "...\lib\ssl.py", line 944, in do_handshake
self._sslobj.do_handshake()
ssl.SSLCertVerificationError: [SSL: CERTIFICATE_VERIFY_FAILED] certificate verify failed: certificate has expired (_ssl.c:1108)
The above exception was the direct cause of the following exception:
Traceback (most recent call last):
...
File "...", line 46, in main
client.run(t)
File "...\lib\site-packages\discord\client.py", line 640, in run
return future.result()
File "...\lib\site-packages\discord\client.py", line 621, in runner
await self.start(*args, **kwargs)
File "...\lib\site-packages\discord\client.py", line 584, in start
await self.login(*args, bot=bot)
File "...\lib\site-packages\discord\client.py", line 442, in login
await self.http.static_login(token.strip(), bot=bot)
File "...\lib\site-packages\discord\http.py", line 261, in static_login
data = await self.request(Route('GET', '/users/@me'))
File "...\lib\site-packages\discord\http.py", line 165, in request
async with self.__session.request(method, url, **kwargs) as r:
File "...\lib\site-packages\aiohttp\client.py", line 1012, in __aenter__
self._resp = await self._coro
File "...\lib\site-packages\aiohttp\client.py", line 480, in _request
conn = await self._connector.connect(
File "...\lib\site-packages\aiohttp\connector.py", line 523, in connect
proto = await self._create_connection(req, traces, timeout)
File "...\lib\site-packages\aiohttp\connector.py", line 858, in _create_connection
_, proto = await self._create_direct_connection(
File "...\lib\site-packages\aiohttp\connector.py", line 1004, in _create_direct_connection
raise last_exc
File "..\lib\site-packages\aiohttp\connector.py", line 980, in _create_direct_connection
transp, proto = await self._wrap_create_connection(
File "...\lib\site-packages\aiohttp\connector.py", line 938, in _wrap_create_connection
raise ClientConnectorCertificateError(
aiohttp.client_exceptions.ClientConnectorCertificateError: Cannot connect to host discordapp.com:443 ssl:True [SSLCertVerificationError: (1, '[SSL: CERTIFICATE_VERIFY_FAILED] certificate verify failed: certificate has expired (_ssl.c:1108)')]
Checklist
- I have searched the open issues for duplicates.
- I have shown the entire traceback, if possible.
- I have removed my token from display, if visible.
System Information
- Python v3.8.2-final
- discord.py v1.3.3-final
- aiohttp v3.6.2
- websockets v8.1
- system info: Windows 8.1 6.3.9600
About
Problem with certification probably on Discord side, but discord.py still tries to access discordapp, so maybe it can be problem. Also I am looking for solution.
Also it is not only my issue. here is stackoverflow question about it.
About this issue
- Original URL
- State: closed
- Created 4 years ago
- Comments: 45 (11 by maintainers)
Windows:
The method that has had success in the help channels is the following:
Download the required certificate manually: https://crt.sh/?id=2835394 The above link is provided by Sectigo. This is where the actual download button is.
Once it has downloaded, double click it to install it. I believe installing it to the local computer and not the running user is the correct way to proceed, correct me if I am wrong there.
Please don’t recommend for users to manually add certs not issued with the intention of being used as a root CA as a trustable entity to the trusted root CA store. This will appear to fix the connection issue but has massive security implications beyond that. The trusted root authorities should not be modified in this way.
I generally agree with the above, however I’d like to point out that Sectigo, the root Certificate Authority in this case, released 4 “modern” certificates that should be installed. You can find more information in their release about this expiration here: https://support.sectigo.com/articles/Knowledge/Sectigo-AddTrust-External-CA-Root-Expiring-May-30-2020
In my case only 3 of the modern certs were installed and I was missing the COMODO ECC Certification Authority root cert. This just so happens to be the root of the cert issued by Cloudflare for Discord.com this morning. Per that link from Sectigo, I was able to obtain the certificate by going to https://crt.sh/?id=2835394. There is a small link on the left side of the page that says “Download Certificate: PEM”. This is a site operated by Sectigo.
My guess is that either MS or Sectigo screwed up here and somehow this 1 of 4 certs did not get included into some kind of update. After installing this certificate I’m back up and running just fine.
A root certificate expired today on the Windows chain. Chances are there’ll be an update soon to fix it on Windows.
https://crt.sh/?id=1
Here is a solution which doesn’t compromise the security of the entire system, but is of course a TOTAL HACK and I hereby inform you that you alone bear the full responsibility for any damage that occurs from using it. It basically tells your bot to not use the certificates known to your OS but instead others which you download manually.
Open https://discord.com/ in Firefox, Chrome or whatever other browser. Download the whole certificate chain (PEM file). It’s important that you get the whole chain. You can also use curl.
You’ll need to modify the source of the discord.py module so I recommend to install it in the virtual environment of your bot (through pipenv) so your main Python installation is unaffected. But it doesn’t really matter because you use the module only for your bots.
Open the file http.py of the module.
Add
import sslto the beginning of the file.Add the following line to HTTPClient.__init__ method, the position is not relevant, I added it right after
self.use_clock = not unsync_clock:before each of the source lines:
https://github.com/Rapptz/discord.py/blob/master/discord/http.py#L132 https://github.com/Rapptz/discord.py/blob/master/discord/http.py#L185
Run your bot.
If the chain is not enough, you can download the whole CRT file of Firefox (https://curl.se/docs/caextract.html) and try that instead of the PEM file.
If you’re using macOS go to Macintosh HD > Applications > Python3.X folder (X = whatever version of python you’re using) > double click on “Install Certificates.command” and the issue went away!
is there any fix for this on Mac?
If you’re on macOS you’ll want to go into the python 3.x folder in your Applications and double click
Install Certificates.commandAfter working on it for a few hours, here’s what i came up with:
This fixed it for me, hope it will help everyone still looking for a solution 😃
just install ssl valid from discord.com
Is the error on Mac that the certificate expired, or that it’s just missing? If it’s the latter then https://github.com/Rapptz/discord.py/issues/423#issuecomment-272093801 might solve your issue.
There is no security implications if you use the specific certificate I linked earlier in this thread. Some common sense applies that you should not install anything you don’t need / won’t use, meaning just that one certificate should suffice. Again as I stated before, this is from Sectigo themselves, so if/when Windows releases their Trust Store update, it’s just going to download this exact certificate anyway.
As for the status on the pending update Windows still has to issue: no sign of it yet.
Per Microsoft this root certificate should be included in Win10. Here’s a page about the Microsoft Root Certificate Program: https://docs.microsoft.com/en-us/security/trusted-root/program-requirements
And here’s a list of current participants (as of June 4th 2020): https://ccadb-public.secure.force.com/microsoft/IncludedCACertificateReportForMSFT
Note the inclusion of the certificate I was missing above with a Ctrl-F of “COMODO ECC Certification Authority”. I’m not sure if this was just added or has been in Win10 for a while. I was certainly missing it.
EDIT: Per the release notes from 03/06/2019 here: https://docs.microsoft.com/en-us/security/trusted-root/mar2019 The friendly names of all of these certificates changed at that time. It doesn’t say what they changed to but we can match up the SHA-1 hash from “COMODO \ 9F744E9F2B4DBAEC0F312C50B6563B8E2D93C311” on that page to the same one from this link: https://crt.sh/?id=2835394
So these certs have been around a while. I’m not sure why my machine was missing them as I’m running Win10 Enterprise Build 19041.264 and I ran a Windows update prior to researching any of this.