Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

7x faster performance. Connect thru socket to MySQL database. #3168

Closed
wants to merge 1 commit into from

Conversation

chris001
Copy link
Contributor

@chris001 chris001 commented Feb 20, 2017

Add support for config option to connect to MySQL database by unix domain socket (UDS), for faster performance, when using a locally hosted database, than the only previous option of connecting by network connection to the database server.

This socket upgrade delivers 66% less latency, and 7X more throughput vs. TCP network connection to MySQL through the network interface.

Here you have the results on a single CPU 3.3GHz Linux machine :

TCP average latency: 6 us

UDS average latency: 2 us

PIPE average latency: 2 us

TCP average throughput: 253702 msg/s

UDS average throughput: 1733874 msg/s

PIPE average throughput: 1682796 msg/s

Source: https://github.com/rigtorp/ipc-bench

Description

Check for new config option db_socket, the name of the socket to connect to the mysql database.
If config option db_socket exists and has a value, then connect to MySQL by the name of the socket.

Motivation and Context

Socket connection is preferred over the network connection thru localhost.

How To Test This

  • Add option to config.php, after db_port, called db_socket.
  • Set the value of db_socket to the full path of the mysql socket, which is a special file created by mysql server when it starts.
    To find the full path of the mysql socket, do the following shell command, on debian/ubuntu/mint:
    # cat /etc/mysql/my.cnf | grep socket
    On CentOS/Scientific/RedHat/Fedora:
    # cat /etc/my.cnf | grep socket
    On debian 8, the full path to the mysql 5.6 socket, happens to be: /var/run/mysqld/mysqld.sock.
    On CentOS 7, the full path to the mysql (mariadb) 5.5 socket happens to be, /var/lib/mysql/mysql.sock.
    So on debian 8/ubuntu 14, after the line with 'db_port', you add:
    'db_socket' => '/var/run/mysqld/mysqld.sock',
    And on CentOS 7/RedHat 7/Fedora, after the line 'db_port', you add:
    'db_socket' => '/var/lib/mysql/mysql.sock',

Types of changes

  • Bug fix (non-breaking change which fixes an issue)
  • New feature (non-breaking change which adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to change)

Final checklist

  • My code follows the code style of this project found here.
  • My change requires a change to the documentation.
  • I have read the How to Contribute guidelines.

Check for new config option `db_socket`, the name of the socket to connect to the mysql database.
If config option `db_socket` exists and has a value, then connect to MySQL by the name of the socket.
Socket connection is preferred over the network connection thru localhost.
@chris001 chris001 changed the title Add support to connect to MySQL database by socket. 7x faster performance. Connect thru socket to MySQL database. Feb 21, 2017
@pgorod
Copy link
Contributor

pgorod commented Feb 21, 2017

@chris001 I'd love to test this. Do you know of an easy way to do a simple performance verification? Just to make sure that the traffic is actually going through the socket, and that there is some observable advantage?

@pgorod
Copy link
Contributor

pgorod commented Feb 21, 2017

My initial tests aren't making much sense to me...

First of all, I introduced the changes, and edited config.php, and the SuiteCRM app works fine (though I can't tell if it's faster).

... but then I tried to make sure the traffic was going through the socket, so I changed my.cnf to add option skip-networking. I confirmed that this is taking effect with

mysql -BNe "show global variables like 'skip_networking'" -u root -p

and it shows skip_networking ON (before the change, it showed OFF).

The app still works fine, which is what I expected: we don't need networking, we're going through the socket.

But when I removed the new socket setting from config.php I was expecting SuiteCRM not to be able to connect, but still the app works fine (when now, it shouldn't).

All this was done with restarts to MySql and Apache in between. What could be going on? Am I wrong about the meaning of skip_networking?

@gunnicom
Copy link
Contributor

Maybe that is the reason:
"The hostname localhost has a special meaning. It is bound to the use of Unix domain sockets. It is not possible to open a TCP/IP connection using the hostname localhost you must use 127.0.0.1 instead"

http://php.net/manual/de/mysqli.quickstart.connections.php

@pgorod
Copy link
Contributor

pgorod commented Feb 21, 2017

Thanks @gunnicom that seems to make sense. I changed my config.php from localhost to 127.0.0.1 and the app stopped connecting (remember, with skip-networking and no socket connection defined). This makes sense.

Then I removed skip-networking and it started connecting again (through 127.0.0.1 networking, I suppose).

But this leaves the following question: it seems MySql is already using the socket, without this PR, when the db is set as localhost.

P.S. - I'm using MySql 5.7

@gunnicom
Copy link
Contributor

Yes, i think it is exactly how you described.

@gunnerman1
Copy link

On Unix, MySQL programs treat the host name localhost specially, in a way that is likely different from what you expect compared to other network-based programs. For connections to localhost, MySQL programs attempt to connect to the local server by using a Unix socket file. This occurs even if a --port or -P option is given to specify a port number. To ensure that the client makes a TCP/IP connection to the local server, use --host or -h to specify a host name value of 127.0.0.1, or the IP address or name of the local server.
--https://dev.mysql.com/doc/refman/5.7/en/connecting.html

I suppose it would be a good idea to note on setup or at least somewhere in the documentation that "localhost" should be the preffered host over 127.0.0.1 for local db installs. I had no idea of this difference. Cool find.

@pgorod
Copy link
Contributor

pgorod commented Feb 22, 2017

@gunnerman1 I think the best place to do it could be in label LBL_DBCONFIG_MSG2, found in install/language/en_us.lang.php. If I'm not mistaken, that's the tooltip for that field (can somebody check?)

I would change it to something like this:

Name of web server or machine (host) on which the database is located (such as www.mydomain.com). If installing locally, it's better to use localhost than 127.0.0.1, for performance reasons.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

5 participants