The README for ibm_db_sa
only lists DB2 for Linux/Unix/Windows in the "Supported Database" section. So it most likely doesn't work for DB2 for i, at least not right out of the box.
Since you've stated you have IBM System i Access for Windows, I strongly recommend just using one of the drivers that comes with it (ODBC, OLEDB, or ADO.NET, as @Charles mentioned).
Personally, I always use ODBC, with either pyodbc
or pypyodbc
. Either one works fine. A simple example:
import pyodbc
connection = pyodbc.connect(
driver='{iSeries Access ODBC Driver}',
system='11.22.33.44',
uid='username',
pwd='password')
c1 = connection.cursor()
c1.execute('select * from qsys2.sysschemas')
for row in c1:
print row
Now, one of SQLAlchemy's connection methods is pyodbc
, so I would think that if you can establish a connection using pyodbc
directly, you can somehow configure SQLAlchemy to do the same. But I'm not an SQLAlchemy user myself, so I don't have example code for that.
UPDATE
I managed to get SQLAlchemy to connect to our IBM i and execute straight SQL queries. In other words, to get it to about the same functionality as simply using PyODBC directly. I haven't tested any other SQLAlchemy features. What I did to set up the connection on my Windows 7 machine:
Install ibm_db_sa
as an SQLAlchemy dialect
You may be able to use pip
for this, but I did it the low-tech way:
- Download
ibm_db_sa
from PyPI.
As of this writing, the latest version is 0.3.2, uploaded on 2014-10-20. It's conceivable that later versions will either be fixed or broken in different ways (so in the future, the modifications I'm about to describe might be unnecessary, or they might not work).
- Unpack the archive (
ibm_db_sa-0.3.2.tar.gz
) and copy the enclosed ibm_db_sa
directory into the sqlalchemydialects
directory.
Modify sqlalchemydialectsibm_db_sapyodbc.py
- Add the
initialize()
method to the AS400Dialect_pyodbc
class
The point of this is to override the method of the same name in DB2Dialect
, which AS400Dialect_pyodbc
inherits from. The problem is that DB2Dialect.initialize()
tries to set attributes dbms_ver
and dbms_name
, neither of which is available or relevant when connecting to IBM i using PyODBC (as far as I can tell).
- Add the module-level name
dialect
and set it to the AS400Dialect_pyodbc
class
Code for the above modifications should go at the end of the file, and look like this:
def initialize(self, connection):
super(DB2Dialect, self).initialize(connection)
dialect = AS400Dialect_pyodbc
Note the indentation! Remember, the initialize()
method needs to belong to the AS400Dialect_pyodbc
class, and dialect
needs to be global to the module.
Finally, you need to give the engine creator the right URL:
'ibm_db_sa+pyodbc://username:password@host/*local'
(Obviously, substitute valid values for username
, password
, and host
.)
That's it. At this point, you should be able to create the engine, connect to the i, and execute plain SQL through SQLAlchemy. I would think a lot of the ORM stuff should also work at this point, but I have not verified this.