вторник, 8 января 2013 г.

Мини СУБД MySQL на Python

Сегодня решил написать лабораторную работу по Системам Баз Данных (СБД) в которой нужно было разработать простейшее клиентское приложение, которое просто бы просматривало все записи из БД MySQL. Я решил пойти немного дальше и написать маленькую консольную СУБД на Python. 

Я прекрасно понимаю, что мало кому эта статья будет интересна (и что тут откровенный быдлокод), но решил все же написать и разобрать ее, что бы в будущем было куда подсматривать. Кто все же осмелится прочесть статью прошу под кат.
Так как в данный момент моей рабочей системой является Windows 7 я скачал и установил http://denwer.ru для MySQL и phpMyAdmin.

Через phpMyAdmin была создана БД - lab1, таблица games_result со структурой:
и пользователь student c правами доступа на insert, select, update и delete.


Для начала нужно было обозначить используемую кодировку: utf-8
# -*- encoding: utf-8 -*-

Модуля для работы с MySQL не было в поставке с Python2.7 поэтому пришлось немного поискать и найти модуль на sourceforge. 
import MySQLdb 
Далее необходимо подключиться к нашей базе данных:
db = MySQLdb.connect(host="localhost", #Адрес mysql сервера
                        user="student", #Пользователь mysql сервер
                        passwd="qwerty", #Пароль пользователя
                        db="lab1") # БД к которой подключаемся

Дальше была проблема с тем, что вместо кириллицы из БД читались непонятные символы, для этого немного поискав был найден рецепт:
db.set_character_set('utf8') 
cursor = db.cursor()  #Тут мы создаем курсор, зачем он?
cursor.execute('SET NAMES utf8')
cursor.execute('SET CHARACTER SET utf8')
cursor.execute('SET character_set_connection=utf8')

Объявляем функцию, которая будет выводить все записи из нашей таблицы:
def showDB():
    cursor.execute("SELECT * FROM `games_result`") 
    print "ID\tName\t\t\tCity\t\t\tPoint" 
    for row in cursor.fetchall(): 
        print ("%d\t%s   \t\t%s    \t%d"%(row[0],row[1],row[2],row[3])) 
    main()

Наша главная функция, которая запрашивает команду, которую будем выполнять. Это delete - удалить элемент, insert - добавление новой записи, update - обновление записи, show - вывести содержимое всей таблицы, exit - выход из программы.
raw_input() - чтение введенной пользователем строки.
input() - чтение введенного пользователем числа.
def main():
    print "\nChoose operation (delete, insert, update, show, exit):"
    ans = raw_input()
    chooze(ans)

Функция удаления, в качестве аргумента получает ID записи, которую необходимо удалить из таблицы. Конкатенирует запрос в переменную и с помощью cursor.execute() - выполняет данный запрос.
def delete(dele):
    oper = 'DELETE FROM games_result WHERE ID='+str(dele)
    cursor.execute(oper)
    print "You delete record with ID=",str(dele)
    main()

Функция добавления, в качестве аргумента получает Имя, Город и Кол-во очков.
Создает запрос к БД вставляя необходимые поля в новую запись.
def insert(name,city,point):
    cursor.execute("""INSERT INTO games_result VALUES(NULL, %s,%s,%s)""",[name, city, point])
    main()

Функция обновления записи, в качестве аргументов получают ID, Имя, Город и Кол-во очков.
Ищет и обновляет запись с заданным ID.
def update(id, name, city, point):
    cursor.execute("""UPDATE games_result SET NAME=%s, CITY=%s, POINTS=%s WHERE ID=%s""",[name,city,point,id])
    main()

Эта ужасная функция выбора, обычный, тупой if и ввод необходимых для каждой команды данных.
def chooze(ans):
    if ans == 'delete':
        print "Please enter a ID what string you want to delete from DB"
        dele = input()
        delete(dele)
    elif ans == 'insert':
        print "Enter Name:"
        name=raw_input()
        print "Enter City:"
        city=raw_input()
        print "Enter a Point"
        point=input()
        insert(name,city,point)
    elif ans == 'update':
        print "Enter a ID for what string update info:"
        id=input()
        print "Enter new name:"
        name=raw_input()
        print "Enter new city"
        city=raw_input()
        print "Enter new point"
        point=raw_input()
        update(id, name, city, point)
    elif ans == 'show':
        showDB()
    elif ans == 'exit':
        return
    else:
        print "Enter correct command"
        main()

Вызов главной нашей функции.
main()

Закрываем курсорс и соединение с БД.
cursor.close() 
db.close() 

Как выглядит работа в данной программе:
Choose operation (delete, insert, update, show, exit):
show
ID Name City Point
1 Андрей   Севастополь     99
16 Петров   Киев     99
4 Нагорный   Джанкой     93
5 Калачев   Симферополь     98
6 Дубинин   Евпатория     97

Choose operation (delete, insert, update, show, exit):
delete
Please enter a ID what string you want to delete from DB
1
You delete record with ID= 1

Choose operation (delete, insert, update, show, exit):
show
ID Name City Point
16 Петров   Киев     99
4 Нагорный   Джанкой     93
5 Калачев   Симферополь     98
6 Дубинин   Евпатория     97

Choose operation (delete, insert, update, show, exit):
insert
Enter Name:
Andrey
Enter City:
Sidorov
Enter a Point
201

Choose operation (delete, insert, update, show, exit):
update
Enter a ID for what string update info:
6
Enter new name:
Dubinin
Enter new city
Evpatory
Enter new point
12

Choose operation (delete, insert, update, show, exit):
show
ID Name City Point
17 Andrey   Sidorov     201
16 Петров   Киев     99
4 Нагорный   Джанкой     93
5 Калачев   Симферополь     98
6 Dubinin   Evpatory     12

Choose operation (delete, insert, update, show, exit):
exit

1 комментарий: