The Python DB-API
To begin, the program must first import the appropriate Python module for connecting to the database product being used. By convention, all database modules compliant with the Python DB-API have names that end in “db”, e.g., soliddb and oracledb.
The next step is to create an object that represents a database connection. The object has the same name as the module. The information required to open a connection, and its format, varies for different databases. Usually, it includes a user name and password, and some indication of how to find the database server, such as a TCP/IP hostname. If you're using the free trial version of SOLID, UNIX pipes are the only method available to connect to the server, so the code is:
>>> import soliddb
>>> db = soliddb.soliddb('UPipe SOLID',
'amk', 'mypassword')
>>> db
<Solid object at 809bf10>
Next, you should create a cursor object. A cursor object acts as a handle for a given SQL query; it allows retrieval of one or more rows of the result, until all the matching rows have been processed. For simple applications that do not need more than one query at a time, it's not necessary to use a cursor object because database objects support all the same methods as cursor objects. We'll deliberately use cursor objects in the following example. (For more on beginning SQL, see At the Forge by Reuven Lerner in LJ, October, 1997.)
Cursor objects provide an execute() statement that accepts a string containing an SQL statement to be performed. This, in turn causes the database server to create a set of rows that match the query.
The results are retrieved by calling a method whose name begins with fetch, which returns one or more matching rows or “None” if there are no more rows to retrieve. The fetchone() method always returns a single row, while fetchmany() returns a small number of rows and fetchall() returns all the rows that match.
For example, to list all the seminars being offered, do the following:
>>> cursor = db.cursor()
>>> # List all the seminars
>>> cursor.execute('select * from Seminars')
>>> cursor.fetchall(
[(4, 'Web Commerce', 300.0, 26),
(1, 'Python Programming', 200.0, 15),
(3, 'Socket Programming', 475.0, 7),
(2, 'Intro to Linux', 100.0, 32),
]
A row is represented as a tuple, so the first row returned is:
(4, 'Web Commerce', 300.0, 26)Notice that the rows aren't returned in sorted order; to do that, the query has to be slightly different (just add order by ID). Because they return multiple rows, the fetchmany() and fetchall() methods return a list of tuples. It's also possible to manually iterate through the results using the fetchone() method and looping until it returns “None”, as in this example which lists all the attendees for seminar 1:
>>> cursor.execute (
'select * from Attendees where seminar=1')
>>> while (1):
... attendee = cursor.fetchone()
... if attendee == None: break
... print attendee
...
('Albert', 1, 'no')
('Beth', 1, 'yes')
('Elaine', 1, 'yes')
SQL also lets you write queries that operate on multiple tables, as
in this query, which lists the seminars that Albert will be
attending:
>>> cursor.execute("""select Seminars.title
... from Seminars, Attendees
... where Attendees.name = 'Albert'
... and Seminars.ID = Attendees.seminar""")
>>≫ cursor.fetchall()
[('Python Programming',), ('Web Commerce',)]
Now that we can get information out of the database, it's time to
start modifying it by adding new information. Changes are made by
using the SQL insert and
update statements. Just like queries, the SQL
statement is passed to the execute() method of a cursor object.
Before showing how to add information, there's one subtlety to be noted that occurs when a task requires several different SQL commands to complete. Consider adding an attendee to a given seminar. This requires two steps. In one step, a row must be added to the Attendees table giving the person's name, the ID of the seminar they'll be attending and whether or not they've paid. In the other step, the places_left value for this seminar should be decreased by one, because there's room for one less person. SQL has no way to combine two commands, so this requires two execute() calls. But what if something happens and the second command isn't executed—perhaps, because the computer crashed, the network died or there was a typo in the Python program? The database is now inconsistent: an attendee has been added, but the places_left column for that seminar is now wrong.
Most databases offer transactions as a solution for this problem. A transaction is a group of commands: either all of them are executed, or none of them are. Programs can issue several SQL commands as part of a transaction and then commit them, (i.e., tell the database to apply all these changes simultaneously). Alternatively, the program can decide that something's wrong and roll back the transaction without making the changes.
For databases that support transactions, the Python interface silently starts a transaction when the cursor is created. The commit() method commits the updates made using that cursor, and the rollback() method discards them. Each method then starts a new transaction. Some databases don't have transactions, but simply apply all changes as they're executed. On these databases, commit() does nothing, but you should still call it in order to be compatible with those databases that do support transactions.
Listing 2 is a Python function that tries to get all this right by committing the transaction once both operations have been performed. Calling this function is simple:
addAttendee('George', 4, 'yes')
We can verify that the change was performed by checking the listing for seminar #4, and listing its attendees. This produces the following output:
Seminars: 4 'Web Commerce' 300.0 25 Attendees: Albert 4 no Dale 4 yes Felix 4 no George 4 yesNote that this function is still buggy if more than one process or thread tries to execute it at the same time. Database programming can be potentially quite complex.
With this standardized interface, it's not difficult to write all kinds of Python programs that act as easy-to-use front ends to a database.
Andrew Kuchling works as a web site developer for Magnet Interactive in Washington, D.C. One of his past projects was a sizable commercial site that was implemented using Python on top of an Illustra database. He can be reached via e-mail at akuchling@acm.org.
Realizing the promise of Apache® Hadoop® requires the effective deployment of compute, memory, storage and networking to achieve optimal results. With its flexibility and multitude of options, it is easy to over or under provision the server infrastructure, resulting in poor performance and high TCO. Join us for an in depth, technical discussion with industry experts from leading Hadoop and server companies who will provide insights into the key considerations for designing and deploying an optimal Hadoop cluster.
Sponsored by AMD
Built-in forensics, incident response, and security with Red Hat Enterprise Linux 6
Every security policy provides guidance and requirements for ensuring adequate protection of information and data, as well as high-level technical and administrative security requirements for a system in a given environment. Traditionally, providing security for a system focuses on the confidentiality of the information on it. However, protecting the data integrity and system and data availability is just as important. For example, when processing United States intelligence information, there are three attributes that require protection: confidentiality, integrity, and availability.
Learn more about catching the bad guy in this free white paper.
Sponsored by DLT Solutions
| Designing Electronics with Linux | May 22, 2013 |
| Dynamic DNS—an Object Lesson in Problem Solving | May 21, 2013 |
| Using Salt Stack and Vagrant for Drupal Development | May 20, 2013 |
| Making Linux and Android Get Along (It's Not as Hard as It Sounds) | May 16, 2013 |
| Drupal Is a Framework: Why Everyone Needs to Understand This | May 15, 2013 |
| Home, My Backup Data Center | May 13, 2013 |
- Designing Electronics with Linux
- Making Linux and Android Get Along (It's Not as Hard as It Sounds)
- Dynamic DNS—an Object Lesson in Problem Solving
- New Products
- Using Salt Stack and Vagrant for Drupal Development
- Validate an E-Mail Address with PHP, the Right Way
- Build a Skype Server for Your Home Phone System
- Why Python?
- Tech Tip: Really Simple HTTP Server with Python
- A Topic for Discussion - Open Source Feature-Richness?
- Not free anymore
1 hour 8 min ago - Great
4 hours 55 min ago - Reply to comment | Linux Journal
5 hours 3 min ago - Understanding the Linux Kernel
7 hours 18 min ago - General
9 hours 48 min ago - Kernel Problem
19 hours 51 min ago - BASH script to log IPs on public web server
1 day 18 min ago - DynDNS
1 day 3 hours ago - Reply to comment | Linux Journal
1 day 4 hours ago - All the articles you talked
1 day 6 hours ago
Enter to Win an Adafruit Pi Cobbler Breakout Kit for Raspberry Pi

It's Raspberry Pi month at Linux Journal. Each week in May, Adafruit will be giving away a Pi-related prize to a lucky, randomly drawn LJ reader. Winners will be announced weekly.
Fill out the fields below to enter to win this week's prize-- a Pi Cobbler Breakout Kit for Raspberry Pi.
Congratulations to our winners so far:
- 5-8-13, Pi Starter Pack: Jack Davis
- 5-15-13, Pi Model B 512MB RAM: Patrick Dunn
- 5-21-13, Prototyping Pi Plate Kit: Philip Kirby
- Next winner announced on 5-27-13!
Free Webinar: Hadoop
How to Build an Optimal Hadoop Cluster to Store and Maintain Unlimited Amounts of Data Using Microservers
Realizing the promise of Apache® Hadoop® requires the effective deployment of compute, memory, storage and networking to achieve optimal results. With its flexibility and multitude of options, it is easy to over or under provision the server infrastructure, resulting in poor performance and high TCO. Join us for an in depth, technical discussion with industry experts from leading Hadoop and server companies who will provide insights into the key considerations for designing and deploying an optimal Hadoop cluster.
Some of key questions to be discussed are:
- What is the “typical” Hadoop cluster and what should be installed on the different machine types?
- Why should you consider the typical workload patterns when making your hardware decisions?
- Are all microservers created equal for Hadoop deployments?
- How do I plan for expansion if I require more compute, memory, storage or networking?




Comments
Iteration?
I would rather do something more like this
cursor.execute(...)
for i in cursor:
...
clearer code
why
while (1):instead of
while 1:and
if attendee == None: breakinstead of
if attendee is None: breakif you want to give an example, please give a good one, not just something that works, show how to write pythonic code
I wonder if you thought at all before posting
Sometimes, things are not as they appear to the casual, shallow minded observer.
AMK is no 'newbie' to Python. Rather like a skilled sensei teaching young would-be samurai, he simplied his technique so as not to distract his students with complexity but rather to let them focus on his lesson one simple point at a time.
Huahweuahwa
The real pythonic way of "saying" [if attendee is None: break]
is [if not attendee: break]
Remember, nothing is so good that can not be better . . .
If you want to correct someone, do this better next time.
Hey Andrew, nice code, your tutorial is the only link at PyGreSQL page, continue helpping people that are realy capable of learnning something.
Huahweuahwa
The real pythonic way of "saying" [if attendee is None: break]
is [if not attendee: break]
Remember, nothing is so good that can not be better . . .
If you want to correct someone, do this better next time.
You certainly don't know who
You certainly don't know who AMK is.
Well, as a python
Well, as a python programmer, it could have been better, but since it's about using the API, and not how to write good python, it's still a good example.
Re: The Python DB-API
This is useful. Thanks.
Re: The Python DB-API
Good writing-hack. Thanx a lot, 'cause it was so useful.
LINUX POWER TO U ;o)
This is really helpful to beg
This is really helpful to beginners to give them idea what is like DB programming with Python. Thanks!
nice :) There's a small ty
nice :)
There's a small typo in one of the code samples where &Gt appears literally (it comes out as >>&Gt instead of >>>)
Thanks.
This is really helpful to beg
This is really helpful to beginners to give them idea what is like DB programming with Python. Thanks!