65

The setup...

Trying to set up a clean Mac os X 10.6 install to develop python/django and I didn't remember running into this on 10.5.

After installing MySQL from the installer on mysql-5.5.8-osx10.6-x86_64.dmg I ran

$ sudo pip install MySQL-python

and it seemed to go smoothly (output below)

Downloading/unpacking MySQL-python
  Downloading MySQL-python-1.2.3.tar.gz (70Kb): 70Kb downloaded
  Running setup.py egg_info for package MySQL-python
    warning: no files found matching 'MANIFEST'
    warning: no files found matching 'ChangeLog'
    warning: no files found matching 'GPL'
Installing collected packages: MySQL-python
  Running setup.py install for MySQL-python
    building '_mysql' extension
    gcc-4.2 -fno-strict-aliasing -fno-common -dynamic -DNDEBUG -g -fwrapv -Os -Wall -Wstrict-prototypes -DENABLE_DTRACE -pipe -Dversion_info=(1,2,3,'final',0) -D__version__=1.2.3 -I/usr/local/mysql/include -I/System/Library/Frameworks/Python.framework/Versions/2.6/include/python2.6 -c _mysql.c -o build/temp.macosx-10.6-universal-2.6/_mysql.o -Os -g -fno-common -fno-strict-aliasing -arch x86_64
    In file included from _mysql.c:36:
    /usr/local/mysql/include/my_config.h:325:1: warning: "SIZEOF_SIZE_T" redefined
    In file included from /System/Library/Frameworks/Python.framework/Versions/2.6/include/python2.6/Python.h:9,
                     from pymemcompat.h:10,
                     from _mysql.c:29:
    /System/Library/Frameworks/Python.framework/Versions/2.6/include/python2.6/pymacconfig.h:33:1: warning: this is the location of the previous definition
    In file included from _mysql.c:36:
    /usr/local/mysql/include/my_config.h:419:1: warning: "HAVE_WCSCOLL" redefined
    In file included from /System/Library/Frameworks/Python.framework/Versions/2.6/include/python2.6/Python.h:8,
                     from pymemcompat.h:10,
                     from _mysql.c:29:
    /System/Library/Frameworks/Python.framework/Versions/2.6/include/python2.6/pyconfig.h:803:1: warning: this is the location of the previous definition
    gcc-4.2 -Wl,-F. -bundle -undefined dynamic_lookup build/temp.macosx-10.6-universal-2.6/_mysql.o -L/usr/local/mysql/lib -lmysqlclient_r -lpthread -o build/lib.macosx-10.6-universal-2.6/_mysql.so -arch x86_64
    warning: no files found matching 'MANIFEST'
    warning: no files found matching 'ChangeLog'
    warning: no files found matching 'GPL'
Successfully installed MySQL-python
Cleaning up...

after this I tried:

$ python -c "import MySQLdb"

and it crapped out on me with:

Traceback (most recent call last):
  File "<string>", line 1, in <module>
  File "/Library/Python/2.6/site-packages/MySQLdb/__init__.py", line 19, in <module>
    import _mysql
ImportError: dlopen(/Library/Python/2.6/site-packages/_mysql.so, 2): Library not loaded: libmysqlclient.16.dylib
  Referenced from: /Library/Python/2.6/site-packages/_mysql.so
  Reason: image not found

So on to my question...

What did I do wrong?/What else do I need to do?

Googling (and searching here) for this returns a lot of results getting this error message with Ruby not too many with Python tho.

rennat
  • 2,529
  • 3
  • 26
  • 30

7 Answers7

97

Just set the DYLD_LIBRARY_PATH after running pip install or easy_install:

export DYLD_LIBRARY_PATH=/usr/local/mysql/lib/

Should do the job assuming your MySQL installation lives under /usr/local/mysql.

lukmdo
  • 7,489
  • 5
  • 30
  • 23
  • 1
    This fix worked for me but I have to do it every time I try to start up django. Is there a place where I can set this (save it in a file) that will make it a permanent setting? – thomallen Feb 13 '11 at 21:15
  • 2
    @thomallen if you use `virtualenv` you could set/unset it in your `bin/activate` script, otherwise I would recommend `~/.bash_profile`. – lukmdo Feb 14 '11 at 21:49
  • `which mysql /usr/local/bin/mysql` so my path should be `export DYLD_LIBRARY_PATH=/usr/local/bin/mysql` right? – Ava Aug 26 '13 at 20:19
  • @Ava this is most likely a symbolic link only. Check where it is pointing `ls -l \`which mysql\`` and most likely you will find a **lib** folder there like `/usr/local/mysql/lib/` – lukmdo Aug 28 '13 at 13:08
56

_mysql.so refers to libmysqlclient.16.dylib. That is, the shared library that serves as the bridge between Python and the MySQL client library, _mysql.so, refers to the dynamic library for the MySQL client library, and that library cannot be loaded for some reason.

Questions you need to answer:

  • Is there a libmysqlclient.16.dylib anywhere on your system? If not, you need to install the MySQL client software.
  • If so, is the directory containing that library in your DYLD_LIBRARY_PATH setting? If not, try adding it.
  • If so, you'll have to ensure that the libmysqlclient.16.dylib file is not corrupt. My copy, installed in /opt/local/lib/mysql5/mysql/libmysqlclient.16.dylib, courtesy of MacPorts, has MD5 signature c79ee91af08057dfc269ee212915801a and is 1,462,376 bytes in size. What does your copy look like?
Brian Clapper
  • 25,705
  • 7
  • 65
  • 65
  • 1
    Thanks very much Brian! My copy is at /usr/local/mysql-5.5.8-osx10.6-x86_64/lib/libmysqlclient.16.dylib, is 3,787,328 bytes and has an MD5 sig 9007ca637b74fd2b6c91c681cd4f22b0 so it's definitely different... But my DYLD_LIBRARY_PATH was empty, adding /usr/local/mysql-5.5.8-osx10.6-x86_64/lib/ to it seems to have gotten me running again. Is there a reason the DYLD_LIBRARY_PATH was blank before this? – rennat Dec 30 '10 at 03:50
  • 1
    It's empty by default, I believe. Mine's empty, too, but I haven't actually tried to load the mysql library in Python for awhile. Take a look at the man page for `dyld` (`man dyld`), and look at the documentation for `DYLD_LIBRARY_PATH`. – Brian Clapper Dec 30 '10 at 04:20
  • 30
    I had a similar issue on Snow Leopard 10.6.6, w/Xcode4 (no PPC suport), I ended up having to add DYLD_LIBRARY_PATH to my bash profile as so: ``export DYLD_LIBRARY_PATH=/usr/local/mysql/lib:$DYLD_LIBRARY_PATH``. Never had to do that in previous installs. I hate how old and clunky this package it. – Ben Keating Mar 20 '11 at 17:06
  • The suggestion to set the DYLD_LIBRARY_PATH via export was the final piece for me. Setting it with << DYLD_LIBRARY_PATH=... >> didn't work. This whole process was beyond annoying. – chernevik May 26 '11 at 16:22
  • 2
    In Unix Bourne shell-like shells (such as `bash`), shell variables are local by default; that is, they are not put into the environment, but kept local to the process. The `export` keyword marks a variable as "exported to the environment". Thus, the linker (a subprocess to the shell) can actually see the variable. Just setting DYLD_LIBRARY_PATH, without exporting it, means it's only local to that shell--and, thus, no help in solving this problem. – Brian Clapper May 26 '11 at 19:13
  • Had exactly the same problem, and setting DYLD_LIBRARY_PATH fixed it. Thanks for the clear answer! – danny Jul 11 '11 at 15:09
  • I had this problem too. When in the world will that MySQL-Python package be updated and brought up to par? – 101010 Jan 17 '12 at 19:01
  • @BrianClapper What client software are you talking about? Sequel Pro? Or is there somthing from MYSQL.org that I am not seeing? Thank you. – dpbklyn Feb 29 '12 at 05:06
  • I have the same problem, but adding DYLD_LIBRARY_PATH=/usr/local/mysql/lib:$DYLD_LIBRARY_PATH to my bash_profile or the etc/profile didn't help. I'm on OSX 10.8 – IdeoREX Jul 16 '13 at 17:17
  • `locate libmysqlclient.16.dylib /usr/lib/libmysqlclient.16.dylib /usr/local/Cellar/mysql51/5.1.71/lib/mysql/libmysqlclient.16.dylib` – Ava Aug 26 '13 at 14:36
  • How do I check the MD5 signature of libmysqlclient.16.dylib? – Ava Aug 26 '13 at 20:27
  • Could you please also help me to solve given issue? https://stackoverflow.com/questions/60987782/facing-issue-while-configuring-mysql-with-apache-airflow-in-hadoop – vikrant rana Apr 03 '20 at 05:33
42

After easy_install, I create a soft link that solved the problem

sudo ln -s /usr/local/mysql/lib/libmysqlclient.18.dylib /usr/local/lib/libmysqlclient.18.dylib
scum
  • 3,202
  • 1
  • 29
  • 27
msbanik
  • 541
  • 4
  • 5
8

On my setup (mysql 5.7.x from brew, pyenv), I had a newer lib file libmysqlclient.20.dylib. What worked was to pip uninstall MySQL-python and pip install MySQL-python.

Giannis
  • 486
  • 6
  • 8
8

It can also crop up if your MySQL client is newer than your MySQL-python package. In my case, I had a libmysqlclient_r.18.dylib on my machine, but not a libmysqlclient_r.16.dylib. Running pip search mysql revealed

MySQL-python - Python interface to MySQL INSTALLED: 1.2.3 LATEST: 1.2.3c1

and running pip install --upgrade MySQL-python fixed my problem.

Catherine Devlin
  • 7,383
  • 2
  • 25
  • 17
  • 1
    This fixed the same problem as the above dynlib hack did. Seems like the default version that's installed with pip install MySQL-python is 1.2.3, not the latest version 1.2.3c1. To get the latest version use: pip install MySQL-python==1.2.3c1 – Emil Stenström Oct 23 '11 at 22:08
  • 2
    Great catch, this was my issue. It's worth mentioning that --upgrade didn't actually seem to upgrade it properly, whereas using install MySQL-python==[latest version] did – G.S. Jan 24 '13 at 21:06
  • I had the same issue as @G.Moore --upgrade didn't seem to catch the new .dylib reference. `pip uninstall MySQL-python && pip install MySQL-python` seems to work as well. – Lucian Thorr Jul 12 '16 at 16:10
7

On the latest version of MySQL 5.7.9 it's no support from MySQL-python and I used the PyMySQL library instead. Also I added in manage.py (in Django project) these lines to emulate API of MySQL-python:

try:
    # load MySQLdb interface emulation
    import pymysql
    pymysql.install_as_MySQLdb()
except ImportError:
    pass
Anton Danilchenko
  • 2,318
  • 1
  • 25
  • 24
0

For those like me who need - or have - both MySQLdb & PyMySQL installed (in my case, I needed to have both installed because I use PyMySQL to connect to my local MySQL instances, and MySQLDb for remote/live instances):

Be sure you're using the right URI scheme. To access the local instances:

LOCAL_DATABASE_URI = 'mysql+pymysql://username:password@hostname/dbname'

and for live:

REMOTE_DATABASE_URI = 'mysql+mysqldb://username:password@hostname/dbname'

Making this distinction solved the issue for me

kip2
  • 6,473
  • 4
  • 55
  • 72