Exempt local user for SSL connection on MySQL server - mysql

I have managed to have turned on SSL connection (require_secure_transport=ON) on MySQL server 5.7. It works fine for both remote and localhost users. However, I don't want the localhost users connected via SSL connection. However can I exempt the local user from the SSL requirement? thanks

I believe the only way to do this would be to update the global configuration to require_secure_transport=OFF and then for every remote user set REQUIRE SSL flag. Essentially switching to an opt-in type of setup for SSL.
The issue with this is you'd have to remember to add this flag every time you add a new remote user, and could easily be forgotten. May be safer bet to resolve any issues with connecting over SSL locally instead.

Related

Is there any documentation around this PyMysql/Mysql behavior?

This is the pymysql code I am using to connect to the database. I am testing with an AWS RDS Mysql instance with Mysql verison 5.7.22. I am getting the certificate from https://docs.aws.amazon.com/AmazonRDS/latest/UserGuide/UsingWithRDS.SSL.html
pymysql.connect(secret_dict['host'], user=secret_dict['username'],
passwd=secret_dict['password'], port=port, db=dbname,
connect_timeout=5, ssl={'ca': './rds-combined-ca-bundle.pem'})
This code works with my test database with the user with ssl enabled and the user wo ssl enabled. - (Via ALTER USER 'encrypted_user'#'%' REQUIRE SSL; )
My question is is this pymysql behavior that I am seeing true of any MySQL verison database or documented anywhere? The behavior I am referring to is that if you add the ssl option to the connect call, it should work (successful connection) regardless or not the actual user has SSL required on it. I prefer not to test with every Mysql version :)
From taking a look at the pymysql code, what it seems to do is check if there are any ssl parameters associated with the request, adds it to an ssl map, and then creates a ctx_object from that ssl map and uses that ctx_ object when initializing a socket with the database.
Just found this on the Mysql 7 documentation guide
"On the server side, the --ssl option specifies that the server permits but does not require encrypted connections. This option is enabled by default, so it need not be specified explicitly."
"By default, MySQL client programs attempt to establish an encrypted connection if the server supports encrypted connections, with further control available through the --ssl-mode option:"
"In the absence of an --ssl-mode option, clients attempt to connect using encryption, falling back to an unencrypted connection if an encrypted connection cannot be established. This is also the behavior with an explicit --ssl-mode=PREFERRED option."
"PREFERRED: Establish an encrypted connection if the server supports encrypted connections, falling back to an unencrypted connection if an encrypted connection cannot be established. This is the default if --ssl-mode is not specified."
So I believe what's happening is that pymysql doesn't specify the ssl-mode option so the ssl client side mode being used is PREFERRED which means that the client(pymysql) will try to establish an ssl connection(which I think fails because the user doesn't require it) and then fallback to the unencrypted connection which will be successful.

How to access my newly setup MySQL database (getting "Domain is currently unable to handle this request.")

I just set up a new MySQL database with the MySQL workbench & created a user for it with all necessary privileges. I am using this database for use with my php code. But I can't seem to connect to it on my live server (pages are hosted on windows server 2012). Everything works fine in my local environment with xampp and the new MySQL database is exactly the same as the xampp one. I think I am maybe using the wrong host name or something. As host name I copied the name that is displayed after "Host:" when you click on Server Status in MySQL workbench. The database name, user & password should all be correct. But when my code tries to access the db I get a "The domain page isn’t working. Domain is currently unable to handle this request."
You either have no network connection to the server at all or it is blocked due to firewall or routing misconfiguration.
If you do have network access in general, you might forgot to
FLUSH PRIVILEGES;
or you have not enabled networking over TCP, the default is to listen only to localhost (on unix systems via unix sockets, on microsoft I guess it's simply TCP).
Read about the following configuration parameter which will solve your networking issue:
bind-address
If you have a very old MySQL server version, the parameter is enable-networking but it shouldn't be the case anymore.

Hosted MySql, Views, client Ipaddress change and Access Denied

I have a hosted MySql server with many databases each with many views. I access the server remotely from my office using HeidiSql.
Once in a while the IP address of my office changes. When this happens, I have to add the new office IP address to the server using cPanel and the "Remote MySql" tool so that I can remotely connect again.
However, all of the views have definer: USER#OLD_IP_ADDRESS. If I need to change a view, I get Access Denied. Up to now, I have been deleting the view (yes, i can delete the view) and recreating it, which makes the view's definer USER#NEW_IP_ADDRESS, and then I can edit the view -- until the Ip address changes again.
So, my question is: What is the best practice is an environment like this. Is there a way to define the views once and, without causing a security risk, be able to edit the views after an IP Address change.
Thanks for any guidance.
You could loosen the host in the MySQL user account a bit, according to the IP range of your internet provider. That way, you don't need to change it every time you get a slightly different IP:
user#123.456.789.%
user#123.456.%
This of course loosens the security in this account, but if your password is be a good one, it should not be too risky.
A better way is to make the MySQL server only accessible via SSH. In that case, your MySQL server can be set up using the --skip-networking option, as you always connecting from localhost. Your user account can be user#localhost or user#127.0.0.1, which then would solve your above mentioned problem for all times.
HeidiSQL also supports SSH tunneled MySQL connections, see here for some tutorial.

rDNS security of MySQL remote connections

Consider a MySQL server that accepts remote connections.
What happens if you have a publicly facing MySQL server, and grant access to e.g.:
'sqluser'#'localhost'
If an attacker now sets his rDNS to "localhost", will he able to access this database?
Is there an extra check that also tries to resolve the rDNS back to the IP?
Regardless, database servers shouldn't be internet facing, but this a what-if-question.
It appears that MySQL uses forward-confirmed reverse DNS (FCrDNS) to counter these kind of attacks.
Most of the logic for the hostname checks can be found in sql/hostname.cc. Moreover, several checks are also performed to make sure that the rDNS doesn't contain an IP or is otherwise poisoned.

How to easily and safely connect to postgres or mysql remotely?

I would like to know how can you connect to postgresql in these conditions:
allow you to access them from any location (do IP filtering)
safe connection (no risk on having your password captured)
easy to setup, preferably having to configure only the server for that.
I know that the recommended approach is to used SSH port forwarding, but this requires you to start the port forwarding before trying to connect to these databases.
What is the easiest method to acquire a good enough security without having to do complex setup on the client.
Is there a way to auto enable the port forwarding stuff on demand?
For PostgreSQL you would start by making sure you are using an SSL-enabled build. (I think that is the default for most installers.)
Then you would need to allow the server to accept remote connections by setting listen_addresses (which specifies which IP addresses the server will listen on): http://www.postgresql.org/docs/9.1/interactive/runtime-config-connection.html
The pg_hba.conf file allows you to specify which users can connect to which databases from which IP addresses using which authentication methods. There are a lot of authentication methods from which to choose: http://www.postgresql.org/docs/9.1/interactive/client-authentication.html
Regarding what needs to be done on the client side, the details will depend on what connector you are using from which environment; as an example, the PostgreSQL JDBC driver uses an SSL connection by default if available. To tell the JDBC driver not to accept a connection unless it can use SSL, you set a JDBC connection property: ssl=true. http://jdbc.postgresql.org/documentation/head/ssl-client.html
Sorry, but I don't know how MySQL manages any of this.
I am myself trying to find the answer for Postgre, but here is what you can do for MySQL.
First, you need to enable remote access to your database. You can create a user with remote access ability as follows.
GRANT ALL ON *.* to user#address IDENTIFIED BY 'password';
flush privileges;
More details here.
To add security to this, you can add a 'REQUIRE SSL' to the GRANT command as follows
GRANT ALL ON *.* to user#address IDENTIFIED BY 'password' REQUIRE SSL;
All this needs to be done on the server side. On the client, you just need to provide the required certificates that it will need to connect.
For details on creating certificates, the MySQL site has a step by step guide here