Cannot TLS connect to GCP Cloud SQL(MySQL) using python3 - python-3.x

import ssl
sc = ssl.SSLContext(ssl.PROTOCOL_TLS_CLIENT)
sc.load_verify_locations(cafile='./server-ca.pem')
sc.load_cert_chain(certfile='./client-cert.pem', keyfile='./client-key.pem')
#sc.check_hostname = False
async with aiomysql.create_pool(
host=host,
port=port,
user=user,
password=password,
db=db,
ssl=sc
)
I'm getting an error like this.
ssl.SSLCertVerificationError: [SSL: CERTIFICATE_VERIFY_FAILED]
certificate verify failed: IP address mismatch, certificate is not
valid for 'ip_address'. (_ssl.c:1108)
server-ca.pem, client-cert.pem, and client-key.pem are exported from the connection tab of GCP Cloud SQL.
#mysql --ssl-ca=./server-ca.pem --ssl-cert=./client-cert.pem --ssl-key=./client-key.pem --host=host --user=user --password
This mysql command can be used to access.
I would like you to tell me what the problem is.

Just encountered the same problem. You need to set the parameter check_hostname=False, such that SSL doesn't try to verify it.
ssl = {
'cert': ...,
'key': ...,
'ca': ...,
'check_hostname': False,
}
I'm using PyMySQL. You might look into how that applies to SSLContext in your case.

Related

RabbitMQ' pika handshaking fails when SSL is set

I am setting up the SSL layer on RabbitMQ on both server and clients. But the clients are failing when creating the connection to the server. At this point I am running the RabbitMQ server on a docker locally and the client locally using a conda environment.
Once the RabbitMQ server is up I see that the secure connection is accepting incoming connections:
test-rabbitmq-1 | 2023-01-20 08:22:01.692731+00:00 [info] <0.726.0> started TCP listener on [::]:5672
test-rabbitmq-1 | 2023-01-20 08:22:01.694836+00:00 [info] <0.746.0> started TLS (SSL) listener on [::]:7575
But the client refuses to connect with:
(rabbitmq-test) ➜ RabbitMQ-TSL ✗ python3 test.py
Enter PEM pass phrase: ********
INFO:pika.adapters.utils.connection_workflow:Pika version 1.3.1 connecting to ('127.0.0.1', 7575)
INFO:pika.adapters.utils.io_services_utils:Socket connected: <socket.socket fd=6, family=AddressFamily.AF_INET, type=SocketKind.SOCK_STREAM, proto=6, laddr=('127.0.0.1', 43142), raddr=('127.0.0.1', 7575)>
ERROR:pika.adapters.utils.io_services_utils:SSL do_handshake failed: error=SSLZeroReturnError(6, 'TLS/SSL connection has been closed (EOF) (_ssl.c:997)'); <ssl.SSLSocket fd=6, family=AddressFamily.AF_INET, type=SocketKind.SOCK_STREAM, proto=6, laddr=('127.0.0.1', 43142), raddr=('127.0.0.1', 7575)>
Traceback (most recent call last):
File "/.../.local/lib/python3.10/site-packages/pika/adapters/utils/io_services_utils.py", line 636, in _do_ssl_handshake
self._sock.do_handshake()
File "/usr/lib/python3.10/ssl.py", line 1342, in do_handshake
self._sslobj.do_handshake()
ssl.SSLZeroReturnError: TLS/SSL connection has been closed (EOF) (_ssl.c:997)
ERROR:pika.adapters.utils.connection_workflow:Attempt to create the streaming transport failed: SSLZeroReturnError(6, 'TLS/SSL connection has been closed (EOF) (_ssl.c:997)'); 'localhost'/(<AddressFamily.AF_INET: 2>, <SocketKind.SOCK_STREAM: 1>, 6, '', ('127.0.0.1', 7575)); ssl=True
ERROR:pika.adapters.utils.connection_workflow:AMQPConnector - reporting failure: AMQPConnectorTransportSetupError: SSLZeroReturnError(6, 'TLS/SSL connection has been closed (EOF) (_ssl.c:997)')
ERROR:pika.adapters.utils.connection_workflow:AMQP connection workflow failed: AMQPConnectionWorkflowFailed: 1 exceptions in all; last exception - AMQPConnectorTransportSetupError: SSLZeroReturnError(6, 'TLS/SSL connection has been closed (EOF) (_ssl.c:997)'); first exception - None.
ERROR:pika.adapters.utils.connection_workflow:AMQPConnectionWorkflow - reporting failure: AMQPConnectionWorkflowFailed: 1 exceptions in all; last exception - AMQPConnectorTransportSetupError: SSLZeroReturnError(6, 'TLS/SSL connection has been closed (EOF) (_ssl.c:997)'); first exception - None
ERROR:pika.adapters.blocking_connection:Connection workflow failed: AMQPConnectionWorkflowFailed: 1 exceptions in all; last exception - AMQPConnectorTransportSetupError: SSLZeroReturnError(6, 'TLS/SSL connection has been closed (EOF) (_ssl.c:997)'); first exception - None
ERROR:pika.adapters.blocking_connection:Error in _create_connection().
Traceback (most recent call last):
File "/.../.local/lib/python3.10/site-packages/pika/adapters/blocking_connection.py", line 451, in _create_connection
raise self._reap_last_connection_workflow_error(error)
File "/.../.local/lib/python3.10/site-packages/pika/adapters/utils/io_services_utils.py", line 636, in _do_ssl_handshake
self._sock.do_handshake()
File "/usr/lib/python3.10/ssl.py", line 1342, in do_handshake
self._sslobj.do_handshake()
ssl.SSLZeroReturnError: TLS/SSL connection has been closed (EOF) (_ssl.c:997)
Traceback (most recent call last):
File "/.../test.py", line 16, in <module>
with pika.BlockingConnection(conn_params) as conn:
File "/.../.local/lib/python3.10/site-packages/pika/adapters/blocking_connection.py", line 360, in __init__
self._impl = self._create_connection(parameters, _impl_class)
File "/.../.local/lib/python3.10/site-packages/pika/adapters/blocking_connection.py", line 451, in _create_connection
raise self._reap_last_connection_workflow_error(error)
File "/.../.local/lib/python3.10/site-packages/pika/adapters/utils/io_services_utils.py", line 636, in _do_ssl_handshake
self._sock.do_handshake()
File "/usr/lib/python3.10/ssl.py", line 1342, in do_handshake
self._sslobj.do_handshake()
ssl.SSLZeroReturnError: TLS/SSL connection has been closed (EOF) (_ssl.c:997)
Any idea of what I am not setting properly on pika or at the RabbitMQ server?
On the server side I set the SSL layer at rabbitmq.conf as:
# Enable AMQPS
listeners.ssl.default = 7575
ssl_options.cacertfile = /etc/rabbitmq/cer/ca_certificate.pem
ssl_options.certfile = /etc/rabbitmq/cer/server_certificate.pem
ssl_options.keyfile = /etc/rabbitmq/cer/server_key.pem
ssl_options.verify = verify_peer
ssl_options.fail_if_no_peer_cert = true
# Enable HTTPS
management.listener.port = 15671
management.listener.ssl = true
management.listener.ssl_opts.cacertfile = /etc/rabbitmq/cer/ca_certificate.pem
management.listener.ssl_opts.certfile = /etc/rabbitmq/cer/server_certificate.pem
management.listener.ssl_opts.keyfile = /etc/rabbitmq/cer/server_key.pem
The docker compose file contains:
version: '3.8'
services:
rabbitmq:
image: rabbitmq:3-management
hostname: rabbitmq-server
volumes:
- ./rabbitmq-config/rabbitmq-cert:/etc/rabbitmq/cer
- ./rabbitmq-config/rabbitmq.conf:/etc/rabbitmq/rabbitmq.conf
- ./rabbitmq/data:/var/lib/rabbitmq/mnesia/rabbit#my-rabbit
- ./rabbitmq/logs:/var/log/rabbitmq/log
ports:
- 5672:5672
- 7575:7575
- 15672:15672
Then, and to simply, I am using the demo client from RabbitMQ's guide as:
import logging
import pika
import ssl
from pika.credentials import ExternalCredentials
logging.basicConfig(level=logging.INFO)
context = ssl.create_default_context(
cafile = '/rabbitmq-config/rabbitmq-cert/ca_certificate.pem'
)
context.load_cert_chain(
'/rabbitmq-config/rabbitmq-cert/client_certificate.pem',
'/rabbitmq-config/rabbitmq-cert/client_key.pem'
)
ssl_options = pika.SSLOptions(context, "localhost")
conn_params = pika.ConnectionParameters(
port = 7575,
ssl_options = ssl_options,
credentials = ExternalCredentials()
)
with pika.BlockingConnection(conn_params) as conn:
ch = conn.channel()
ch.queue_declare("foobar")
ch.basic_publish("", "foobar", "Hello, world!")
print(ch.basic_get("foobar"))
Your Python code is set up to do X509 certificate authentication (you're not using username/password but are using ExternalCredentials). However, you have not configured RabbitMQ to accept X509 certificates for authentication (docs).
The Pika docs need to be updated, so I opened this issue - https://github.com/pika/pika/issues/1413
You would probably get a hint of this if you look at the RabbitMQ log file at the time your Python client tries to connect.
In order to enable X509 certificate authentication, do the following:
rabbitmq-plugins enable rabbitmq_auth_mechanism_ssl (docs)
Edit your rabbitmq.conf file and add the following section:
auth_mechanisms.1 = PLAIN
auth_mechanisms.1 = AMQPLAIN
auth_mechanisms.1 = EXTERNAL
Restart RabbitMQ
Add a password-less user that exactly matches the CN= value in your client certificate: rabbitmqctl add_user 'foobar, O=baz'. You can also get this value by attempting to connect after making the above changes. The failed auth attempt will be logged.
If you continue to have problems, I suggest asking on the mailing list as this is not a good forum for detailed analysis.
NOTE: the RabbitMQ team monitors the rabbitmq-users mailing list and only sometimes answers questions on StackOverflow.

ssl.SSLCertVerificationError: [SSL: CERTIFICATE_VERIFY_FAILED] certificate verify failed: self signed certificate in certificate chain (_ssl.c:1091)

I am using Python 3.7. I have a sockstunnel server running in docker mode, and today from the command-line I would like to have the client started and to talk to that tunnel server, but somehow it fails. here is my client code looks like:
import asyncio
...
def socks_tunnel_client(tunnel_host, tunnel_port, socks_host, ssl_ca_file, ssl_cert_file, ssl_key_file):
ssl_ctx_client = ssl.create_default_context(ssl.Purpose.SERVER_AUTH)
ssl_ctx_client.check_hostname = False
ssl_ctx_client.options |= (
ssl.OP_NO_TLSv1 | ssl.OP_NO_TLSv1_1 | ssl.OP_NO_COMPRESSION
)
ssl_ctx_client.set_ciphers("ECDHE-RSA-AES128-GCM-SHA256")
ssl_ctx_client.load_verify_locations(ssl_ca_file)
ssl_ctx_client.load_cert_chain(certfile=ssl_cert_file, keyfile=ssl_key_file)
loop = asyncio.get_event_loop()
# Each client connection will create a new protocol instance
coro_tunnel = loop.create_connection(
lambda: TunnelServer(is_server=False),
tunnel_host,
tunnel_port,
ssl=ssl_ctx_client,
)
loop.run_until_complete(coro_tunnel)
...
I have provided an ssl_ca_file file to make that client call. and when it is to step at line of "loop.run_until_complete(coro_tunnel)", it fails with such messages:
loop.run_until_complete(coro_tunnel)
File "/usr/lib/python3.7/asyncio/base_events.py", line 587, in run_until_complete
return future.result()
File "/usr/lib/python3.7/asyncio/base_events.py", line 989, in create_connection
ssl_handshake_timeout=ssl_handshake_timeout)
File "/usr/lib/python3.7/asyncio/base_events.py", line 1017, in _create_connection_transport
await waiter
File "/usr/lib/python3.7/asyncio/sslproto.py", line 530, in data_received
ssldata, appdata = self._sslpipe.feed_ssldata(data)
File "/usr/lib/python3.7/asyncio/sslproto.py", line 189, in feed_ssldata
self._sslobj.do_handshake()
File "/usr/lib/python3.7/ssl.py", line 774, in do_handshake
self._sslobj.do_handshake()
ssl.SSLCertVerificationError: [SSL: CERTIFICATE_VERIFY_FAILED] certificate verify failed: self signed certificate in certificate chain (_ssl.c:1091)
So my questions:
What does that mean, and how to solve that issue ?
"IF" the provided ssl_ca_file not good enough,(I was told to use this file, but I am not 100% sure), is there a way to by-pass this checking ? Someone mentioned to set "ssl_verify=False" to work around, but I could not figure out how to make this happen.
Thanks a lot for the help.
Jack

Yubico YubiHSM2 connector with HTTPS access

I use Win10 for my experiments.
I want to create HTTPS access between yubihsm-shell and yubihsm-connector.
Official guidelines are not very detailed but after a while I found some relevant information in https://github.com/Yubico/yubihsm-shell/issues/5
I used openssl and created private key (privkey.pem), certificate signing request (csr.csr) and certificate (hsm_cert.pem). The certificate is self signed.
I started yubihsm connector via:
yubihsm-connector.exe -d -l localhost:54321 --cert=hsm_cert.pem --key=privkey.pem
I open up my web browser and I type URL:
https://localhost:54321/connector/status
I get correct message:
status=OK
serial=*
version=3.0.1
pid=12920
address=localhost
port=54321
Next I tried yubishell via following:
yubihsm-shell.exe --connector=https://localhost:54321 --cacert=hsm_cert.pem
yubihsm> connect
Failed setting HTTPS CA
The certificate I gave to YubiHSM shell is the same self signed certificate I started connector with.
Certificate signing request was created with following configuration file:
[ req ]
default_bits = 2048
distinguished_name = req_distinguished_name
req_extensions = v3_req
[ req_distinguished_name ]
countryName = #deleted-due-to-privacy
countryName_default = #deleted-due-to-privacy
countryName_min = 2
countryName_max = 2
localityName = #deleted-due-to-privacy
organizationalUnitName = #deleted-due-to-privacy
commonName = localhost
commonName_max = 64
emailAddress = #deleted-due-to-privacy
emailAddress_max = 40
[ v3_req ]
basicConstraints = CA:TRUE
keyUsage = digitalSignature, keyCertSign
certificate extension file looks like:
authorityKeyIdentifier=keyid,issuer
basicConstraints=CA:TRUE
keyUsage = digitalSignature, nonRepudiation, keyCertSign, keyAgreement
My questions:
How shall I create the X509 certificate for YubiHSM connector?
How shall I give certificate to YubiHSM shell so that it can connect to connector via HTTPS?

Certificate verify failed: unable to get local issuer certificate (_ssl.c:1051) Python

I am trying to connect to a websocket and even though I have updated the certificates, I still cannot connect to the websocket:
python3 -m pip install --upgrade --user certifi
Requirement already up-to-date: certifi in /Users/t**/Library/Python/3.7/lib/python/site-packages (2020.4.5.1)
This is the code:
import asyncio
import logging
import websockets
from websockets import WebSocketClientProtocol
logging.basicConfig(level=logging.INFO)
async def consumer_handler(websocket: WebSocketClientProtocol) -> None:
async for message in websocket:
log_message(message)
async def consume(hostname: str) -> None:
websocket_resource_url = f'wss://{hostname}'
async with websockets.connect(websocket_resource_url) as websocket:
await consumer_handler(websocket)
def log_message(message: str) -> None:
logging.info(f'Message: {message}')
if __name__ == '__main__':
asyncio.run(consume(hostname='echo.websocket.org'))
That is the last part of the return:
File "/Library/Frameworks/Python.framework/Versions/3.7/lib/python3.7/ssl.py", line 763, in do_handshake
self._sslobj.do_handshake()
ssl.SSLCertVerificationError: [SSL: CERTIFICATE_VERIFY_FAILED] certificate verify failed: unable to get local issuer certificate (_ssl.c:1051)
Any idea why?

How to fix ssl connection issue :" ssl.SSLError: [SSL] PEM lib (_ssl.c:3337)

I know there have been similar questions around and i have looked through them and ended up asking again.
To explain the problem at hand:
I have to establish a secured connection to a server
for which i have been given with a PRIVATE key, Certificate and a CA certificate.
I put all of these in one file called "one.pem"
and here is the code i wrote to establish a connection.
import socket
import ssl
import os
HOST, PORT, CERT, KEY= 'XX.XX.XX.XX', 1234, "one.pem", "private.pem"
exists = os.path.exists(CERT)
print(exists)
exists = os.path.exists(KEY)
print(exists)
context = ssl.SSLContext(ssl.PROTOCOL_TLS_CLIENT)
context.load_cert_chain(certfile=CERT, keyfile=None, password=None)
context.verify_mode = ssl.CERT_REQUIRED
with socket.socket(socket.AF_INET, socket.SOCK_STREAM, 0) as sock:
with context.wrap_socket(sock, server_hostname=HOST,certfile=CERT) as ssock:
print(ssock.version())
try:
ssock.connect((HOST, PORT))
except ssl.SSLError as err:
print("Error Connecting : {}".format(str(err)))
i took examples from here
Any hints, ideas are welcome.
Edit:
This is how my "one.pem" looks like ( it is in the same folder as the python file)
-----BEGIN RSA PRIVATE KEY-----
... (private key in base64 encoding) ...
-----END RSA PRIVATE KEY-----
-----BEGIN CERTIFICATE-----
... (certficte in base64 encoding) ...
-----END CERTIFICATE----
-----BEGIN CERTIFICATE-----
... (CA certficte in base64 encoding) ...
-----END CERTIFICATE----
Edit:
error message :
Traceback (most recent call last):
File "ssl_connect.py", line 16, in <module>
context.load_cert_chain(certfile=CERT)
ssl.SSLError: [SSL] PEM lib (_ssl.c:3337)

Resources