Yii Migration Tool No such file or directory
I develop under Windows when I'm and home and in the office but when I'm at out and about I develop on my Mac Book Pro. While both run XAMPP, I recently came across a difference between the Windows and Mac versions while I was using Yii2 Framework, but I understand that this happens while using Yii1 too.
The problem manifests itself with the following Exception message from the Yii Connection
class:
Yii Migration Tool (based on Yii v2.0.2)
Exception 'yii\db\Exception' with message 'SQLSTATE[HY000] [2002] No such file or directory'
in /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/db/Connection.php:539
Stack trace:
#0 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/db/Connection.php(846): yii\db\Connection->open()
#1 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/db/Connection.php(833): yii\db\Connection->getMasterPdo()
#2 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/db/Command.php(208): yii\db\Connection->getSlavePdo()
#3 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/db/Command.php(815): yii\db\Command->prepare(true)
#4 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/db/Command.php(350): yii\db\Command->queryInternal('fetchAll', NULL)
#5 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/db/mysql/Schema.php(198): yii\db\Command->queryAll()
#6 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/db/mysql/Schema.php(97): yii\db\mysql\Schema->findColumns(Object(yii\db\TableSchema))
#7 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/db/Schema.php(139): yii\db\mysql\Schema->loadTableSchema('migration')
#8 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/console/controllers/MigrateController.php(126): yii\db\Schema->getTableSchema('{{%migration}}', true)
#9 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/console/controllers/BaseMigrateController.php(607): yii\console\controllers\MigrateController->getMigrationHistory(NULL)
#10 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/console/controllers/BaseMigrateController.php(99): yii\console\controllers\BaseMigrateController->getNewMigrations()
#11 [internal function]: yii\console\controllers\BaseMigrateController->actionUp(0)
#12 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/base/InlineAction.php(55): call_user_func_array(Array, Array)
#13 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/base/Controller.php(151): yii\base\InlineAction->runWithParams(Array)
#14 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/console/Controller.php(91): yii\base\Controller->runAction('', Array)
#15 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/base/Module.php(455): yii\console\Controller->runAction('', Array)
#16 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/console/Application.php(161): yii\base\Module->runAction('migrate', Array)
#17 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/console/Application.php(137): yii\console\Application->runAction('migrate', Array)
#18 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/vendor/yiisoft/yii2/base/Application.php(375): yii\console\Application->handleRequest(Object(yii\console\Request))
#19 /Applications/XAMPP/xamppfiles/htdocs/rfc/yii-application/yii(31): yii\base\Application->run()
#20 {main}
When connecting to MySQL on a Mac (or a unix box) if you specify host as "localhost" MySQL switches the transport to use file system sockets instead of using a network socket. There are lots of reasons to do this, security and efficiency are the main ones. There is almost no code difference to using a socket on the file system and a socket in the kernel because unix treats them both as file descriptors. Windows treats everything differently and so there is no concept of a file base socket. Windows just uses normal network sockets with all the overhead and security concerns that has.
There are 2 ways you can solve this issue. The first and simplest way to fix this problem is to not use "localhost" in your DSN string. If you use the loopback IP address (127.0.0.1) then MySQL will force itself to use a real network socket in the same way that it would under Windows. So in our Yii2 example, just change the DSN configuration held in: yii2_root/common/config/main-local.php
to:
return [
'components' => [
'db' => [
'class' => 'yii\db\Connection',
//'dsn' => 'mysql:host=localhost;dbname=rfc',
'dsn' => 'mysql:host=127.0.0.1;dbname=rfc',
'username' => 'root',
'password' => '',
'charset' => 'utf8',
],
'mailer' => [
The second way of solving this problem is still quite simple but everything around it is complicated!
The reason why it is happening is because MySQL can not find the "socket" file (as we said earlier), but all the configuration seems to indicate that everything is ok. To cut hours of investigation short and to put yourself out of misery, there are 2 versions of PHP running on your Mac with 2 configurations. As a consequence your Yii installation is using the wrong one (i.e. the command line one and not your XAMPP installation).
When you run your Yii application through your web browser you are running your XAMPP's version of PHP which is why when you look at the phpinfo() via a web page everything looks all right. PHP shows version 5.6.3, the "Loaded Configuration File" is /Applications/XAMPP/xamppfiles/etc/php.ini
and the Configure Command clearly shows --with-mysql-sock=/Applications/XAMPP/xamppfiles/var/mysql/mysql.sock
, and that file exists.
However when you run php from the command line the shell runs through your path and finds a version of php located in /usr/bin
. When you issue the command php --ini
to find out which configuration file is being read you get the following back:
Configuration File (php.ini) Path: /etc
Loaded Configuration File: (none)
Scan for additional .ini files in: /Library/Server/Web/Config/php
Additional .ini files parsed: (none)
Inspecting the /etc
path you will not find a php.ini
. No file means you will get the default configuration. If you issue a command line based php with the -i
option you will see the following configuration instead: PHP shows version 5.5.14, the "Loaded Configuration File" is (none)
and the Configure Command shows --with-mysql-sock=/var/mysql/mysql.sock
To fix this you must change the yii application program to use the correct version of php. Modify yii2_root/yii
and change the env
under which it runs from:
#!/usr/bin/env php
to
#!/usr/bin/env /Applications/XAMPP/xamppfiles/bin/php
Using XAMPP's version of PHP will mean you can keep your localhost
in the DNS and MySQL will use sockets on your production servers instead of the 127.0.0.1
. Forcing your application to open sockets on the localhost
will mean that your firewall configuration will need extra rules and configuration to prevent traffic coming from an external port and bouncing off an internal port in order to talk to a localhost
socket. Using file domain sockets will just mean making sure that the correct file permissions are set on the socket file so that only the MySQL process can talk to it.
No feedback yet
Form is loading...