[LinuxFocus-icon]
<--  | Домой  | Карта  | Индекс  | Поиск

Новости | Архивы | Ссылки | Про LF
[an error occurred while processing this directive]
[Photo of the Author]
автор Diego Alberto Arias Prad
<dariapra(at)yahoo.es>

Об авторе:

Я работаю инженером в области телекоммуникаций в Lugo, Испания. Точно не помню когда я начал использовать Linux, предполагаю, что это произошло в 1995 или 1996 году. До этого момента я использовал Microsoft Windows и даже не знал о существовании Linux. Впервые увидел компьютер с Linux в университете и меня заинтересовала эта операционная система, после этого я установил Linux на свой домашний компьютер. Первым моим дистрибутивом был Slackware.

С тех пор я поработал со многими дистрибутивами Linux и разновидностями BSD. Я программирую на Java и Tcl, использую базы данных и разные серверы - веб и серверы приложений. Но Linux это не только мое хобби, работая в TelefСnica I+D я использовал там эту систему.



Перевод на Русский:
Pukhlyakov Kirill <kirill(at)linuxfocus.org>

Содержание:

 

Знакомство с библиотекой TclMySQL

MySQLTcl

Резюме:

В заметке мы рассмотрим как установить и пользоваться библиотекой MySQLTcl, это библиотека языка Tcl для работы с СУБД MySQL из скриптов, написанных на нем. Версии Tcl, MySQL и библиотеки MySQLTcl использованные для написания заметки соответственно 8.4.2, 4.0.15 и 2.40.

Язык Tcl ( Tool Command Language ) был придуман John Ousterhout [1]. На самом деле Tcl это собственно сам язык и интерпретатор. Это структурный язык использующий три типа данных: строки, списки и массивы. Работая на нем можно использовать регулярные выражения [2], сторонние библиотеки расширения и Tk, пакет для создания графических приложений на Tcl.

СУБД MySQL очень популярный сервер баз данных в сообществе свободно распространяемого программного обеспечения, который не нуждается в представлении.

MySQLTcl это библиотека для языка Tcl с помощью которой можно работать с СУБД MySQL из скриптов, написанных на языке Tcl. В настоящее время авторами и разработчиками этой библиотеки являются Paolo Brutti (Paolo.Bruti at tlsoft.it), Tobias Ritzau (tobri at ida.liu.se) и Artur Trzewick (mail at xdobry.de).

_________________ _________________ _________________

 

Установка библиотеки MySQLTcl

Если Ваша Linux или *BSD система поддерживает пакеты ( напрмер RPM или DEB ) или порты как Crux Linux или FreeBSD, Вы можете использовать их для установки библиотеки MySQLTcl и пропустить этот раздел.

Если это не так или Вы просто предпочитаете устанавливать все "руками", я продемонстрирую Вам как это делал сам. Вы можете использовать это как инструкцию, но не как пошаговое руководство установки. Используя bash дистрибутива Linux Mandrake версии 9.2 делаем следующее:
$ ./configure --with-mysql-lib=/usr/lib
$ make
$ make install
Если что-то происходит не так во время шага "configure", информация об ошибках послужит помощью для их исправления. Обычно проблемная ситуация заключается в следующем - скрипт configure не находит определенные каталоги или файлы. Исправить это можно передавая скрипту пути к этим файлам или каталогам в качестве параметров. Например, устанавливая MySQLTcl на FreeBSD 5.0 я использовал следующие опции:
$ export CPP=/usr/bin/cpp
$ ./configure --with-tcl=/usr/lib/local/tcl8.3
 --with-tclinclude=/usr/local/include/tcl8.3
 --with-mysql-include=/usr/local/include/mysql
 --with-mysql-lib=/usr/local/lib/mysql
$ make
$ make install
Надеюсь Вы заметили, что в этом примере используется Tcl версии 8.3, кроме того - версия библиотеки MySQLTcl 2.15, а сервера MySQL 3.23.54.

 

Основы Tcl

В этом разделе рассмотрим основы Tcl для тех, кому интересна данная заметка, но они не знакомы с ним. Если Вы программируете на Tcl - можете пропустить этот раздел.

Вы можете потренироваться на этих примерах из оболочки Tcl (tclsh).

 

Переменные. Команда и подстановка переменных.

Переменные Tcl создаются с помощью команды set. Рассмотрим несколько примеров:
% set address {Edison Avenue, 83}
Edison Avenue, 83
% set zip_code 48631
48631
В этих двух примерах мы создали две переменные - address и zip_code, и присвоили им значения Edison Avenue, 83 и 48361, которые имеют тип string. Обратите внимание на то, что при присвоении переменной address значение мы использовали фигурные скобки потому, что в нем есть пробел. Получить значения переменных можно командой set:

% set address
Edison Avenue, 83
% set zip_code
48631
Чтобы вывести значение переменной address на экран воспользуемся командой puts:
% puts stdout [set address]
Edison Avenue, 83
Параметр stdout передаваемый команде puts служит для указания вывода в стандартный поток вывода - на экран. Второй передаваемый параметр команде puts это [set address]. Квадратные скобки указывают интерпретатору Tcl, что это другая команда языка Tcl, которая должна быть выполнена перед командой puts - это называется подстановка команд. То же самое можно сделать следующим образом:
% puts stdout $address
Edison Avenue, 83
В этом примере мы выполнили подстановку переменной: символ $ перед переменной указывает на это.

В предыдущем примере мы выяснили, что используя фигурные скобки можно собрать слова в строки. Другая возможность сделать то же самое - использование кавычек ( символ " ). Тем не менее, эти два способа ведут себя по-разному. Посмотрим на примере:
% puts stdout "the zip code is [set address]"
the zip code is 48631
% puts stdout "the zip code is $address"
the zip code is 48631
% puts stdout {the zip code is [set address]}
the zip code is [set address]
% puts stdout {the zip code is $address}
the zip code is $address
Здесь видно, что при использовании фигурных скобок подстановки переменных не происходит, но происходит при использовании кавычек.

Удалить переменные можно командой unset:
% unset address
% set address
can't read "address": no such variable
% unset zip_code
% set zip_code
can't read "zip_code": no such variable

 

Строки в Tcl

Строки являются одним из трех основных типов данных в Tcl. Строка - это набор символов. Строка создается с помощью команды set.

% set surname Westmoreland
Westmoreland
% set number 46.625
46.625
Обе переменные - surname и number имеют тип строка. Работать с переменными этого типа можно командой string. Синтаксис этой команды следующий - string операция значение другие_аргументы. Поясним примерами:
% string length $surname
12
% set surname [string range $surname 0 3]
West
% puts stdout $surname
West
% string tolower $surname
west
В отличие от Java или Pascal Tcl не очень строгий язык программирования. Следующий пример демонстрирует это:
% set number [expr $number + 24.5]
70.125
% string range $number 2 5
.125
С помощью команды expr мы увеличили значение переменной number на 24.5. После этого мы представили переменную number строковой и с помощью команды string вывели последние четыре символа.

 

Списки в Tcl

Списки в Tcl являются разновидностью строк, которые разделены пробелом и интерпретируется соответственное по-своему.

% set friends_list {Fany John Lisa Jack Michael}
Fany John Lisa Jack Michael
% set friends_list [string tolower $friends_list]
fany john lisa jack michael
% set friends_list
fany john lisa jack michael
В Tcl существует набор команд для работы со строками. Рассмотрим несколько примеров:
% lindex 2 $friends_list
lisa
% lrange $friends_list 2 4
lisa jack michael
% set friends_list [lsort -ascii $friends_list]
fany jack john lisa michael
% set friends_list
fany jack john lisa michael
% set friends_list [linsert $friends_list 2 Peter]
fany jack Peter john lisa michael
% string toupper $friends_list
FANY JACK PETER JOHN LISA MICHAEL
Из последнего примера видно, что строки и списки имеют одинаковую структуру.

 

Массивы в Tcl

Массив можно рассматривать особым видом списка с индексом в качестве которого выступает переменная типа "строка". Рассмотрим пример создания массива:

% set phone_numbers(fany) 629
629
% set phone_numbers(michael) 513
513
% set phone_numbers(john) 286
286
Получить значение из массива можно используя команду set как и в предыдущем примере, индекс заключается в круглые скобки.
% set $phone_numers(michael)
513
Информацию о массиве можно получить с помощью команды array. Рассмотрим несколько примеров использования данной команды:
% array size phone_numbers
3
% array names phone_numbers
fany john michael

 

Подключение к базе данных

Для того чтобы выполнять запросы к базе данных из скриптов Tcl сначала надо установить соединение с сервером баз данных. В этой части заметки мы рассмотрим этот вопрос, а также обработку ошибок, которые могут возникнуть в процессе соединения.

 

Соединение с сервером бд

Рассмотрим пример подключения к серверу MySQL из Tcl скрипта:

0:  #!/usr/bin/tclsh8.4
1:
2:  package require mysqltcl
3:  global mysqlstatus
4:
5:  set port {3306}
6:  set host {127.0.0.1}
7:  set user {john_smith}
8:  set password {jsmith_password}
9:
10: set mysql_handler [mysqlconnect -host $host
    -port $port -user $user -password $password]
11:
12: mysqlclose $mysql_handler
Обратите внимание на левую колонку цифр - они не являются частью нашего скрипта, таким образом мы просто пронумеровали строки. Также, в зависимости от используемого вами дистрибутива Linux, вам возможно придется поменять строку #0, указывающую путь к Tcl shell.

Строка #0 указывает shell'у, что данный файл является скриптом Tcl и указывает где искать интерпретатор Tcl.

В строке #2 стоит указание интерпретатору использовать библиотеку MySQLTcl. Например в строке #10 вызывается команда mysqlconnect, если бы мы не указали в строке #2 библиотеку, тогда при вызове данной команды интерпретатор выдал бы ошибку "команда не найдена" ( command not found ).

В строках #5 и #6 инициализируются переменные port и host. В нашем примере port инициализируется значением 3306 ( по умолчанию MySQL прослушивает этот порт ), а host - адресом локального компьютера.

В строках #7 и #8 инициализируются переменные user и password.

В строке #10 устанавливается само соединение и handler сохраняется в переменной mysql_handler, его используют для запросов к бд и закрытия соединения, как показано в строке #12.

 

Обработка ошибок

В предыдущей части мы не рассмотрели строку #3. Сделаем это сейчас.

Выполнение команд библиотеки MySQLTcl может вызывать ошибки. Если мы не поймаем эту ошибку, скрипт может прекратить свою работу. Поменяем немного наш скрипт следующим образом:

10: if [catch {mysqlconnect -host $host -port $port
    -user $user -password $password} mysql_handler] {
11:     puts stderr {error, the database connection could not be established}
12:     exit
13: } else {
14:     mysqlclose mysql_handler
15: }
Если команда set mysql_handler [mysqlconnect -host $host... вызовет ошибку - она будет перехвачена командой catch. Команда catch возвращает 1 в случае возникновения ошибки и 0 в противоположном.

В случае возникновения ошибки сообщение выводится в стандартный поток вывода, в нашем случае это экран. Подобные ошибки возникают в разных обстоятельствах - неправильный пароль, хост, порт и т.д. В подобном случае более подробное описание ошибки будет полезным.

В строке #3 мы объявили глобальную переменную mysqlstatus. Глобальная переменная доступна в любом месте Tcl скрипта. Библиотека MySQLTcl создает глобальный массив mysqlstatus, в котором содержатся следующие элементы:

элемент значение
code Если ошибка не произошла mysqlstatus(code) равен нулю, в противном услучае устанавливается в код ошибки сервера MySQL. Если ошибка возникла, но не является ошибкой MySQL, то значение mysqlstatus(code) устанавливается в -1.

Значение mysqlstatus(code) обновляется после каждого использования команды библиотеки MySQLTcl.
command Команда библиотеки MySQLTcl, выполнение которой породило ошибку, сохраняется в mysqlstatus(command).

Значение mysqlstatus(command) обновляется после каждой команды вызвавшей ошибку, другими словами - mysqlstatus(command) не обновляется после успешной команды.
message Значение mysqltcl(message) обновляется после каждой команды вызвавшей ошибку и заполняется сообщением об ошибке. Также как и mysqlstatus(command), mysqlstatus(message) не обновляется после успешной команды.

Существует еще один элемент в глобальном массиве mysqlstatus, который не связан с обработкой ошибок:

элемент значение
nullvalue Строка, используемая для значения null как результата выполнения SQL запроса. По умолчанию используется пустая строка; musqlstatus(nullvalue) может быть установлена в любое строковое значение.

Таким образом, используя глобальный массив mysqlstatus, предыдущий код можно переписать так, чтобы было понятно что произошло в случае установления соединения с сервером бд:
10: catch {mysqlconnect -host $host -port $port
    -user $user -password $password} mysql_handler
11: if {$mysqltatus(code) != 0} {
12:     puts stderr $mysqlstatus(message)
13: } else {
14:     mysqlclose mysql_handler
15: }
Глобальный массив mysqlstatus можно использовать для обработки большего числа ошибок, не только при установлении соединения с бд.

 

Основные команды библиотеки MySQLTcl

В этой части рассмотрим основные команды библиотеки MySQLTcl и некоторые примеры их использования. Полную информацию по данному вопросу смотрите на man странице MySQLTcl.
Сначала приведем таблицу с данными командами. Параметры подчеркнуты. Если параметр стоит между "?" - он опциональный, символ "|" обозначает "или".

команда краткое описание
mysqlconnect ?option value ...? подключение к бд; возвращает handler, который необходимо использовать в других командах mysqltcl
mysqluse handle dbname ассоциирует MySQL handler с определенной бд
mysqsel handle sql_statement ?-list | -flatlist? отправка SQL команды в бд
mysqlexec handle sql_statement отправка не_select SQL команды в бд
mysqlclose handle закрытие соединения с бд

 

mysqlconnect

Эту команду мы уже обсуждали в разделе "Соединение с сервером бд", но есть один момент, который мы не затронули - параметр -db, он нужен для привязки определенной бд для последующего использования. Посмотрим пример:

% set mysql_handler [mysqlconnect -h 127.0.0.1 -p 3306 \\
  -user john_smith -password jsmith_password -db jsmith_database]
В этом случае при последующем использовании mysql_handler запросы будут будут направлены в бд jsmith_database.

( Пожалуйста, обратите внимание на символы \\, они не являются частью команды; они показывают, что команда продолжается на следующей строке ).

 

mysqluse

Команда служит для смены бд ассоциированной с handler'ом, бд указывается первым параметром.

 

mysqlsel

С помощью данной команды посылается SQL select запрос в бд. если параметр sql_statement не является SQL select запросом - произойдет ошибка.

Можно использовать в этой команде третий ( опциональный ) параметр - list или flat_list. Посмотрим на примере что происходит с выводом, при использовании этого параметра. Предположим в бд есть таблица people:

id first_name last_ name phone
26 Karl Bauer 8245
47 James Brooks 1093
61 Roberto Castro Portela 6507

С помощью команды mysqlsel посылаем SQL запрос в бд:

% mysqlsel $mysql_handler {select first_name, last_name from people order by id asc} -list
{Karl Bauer} {James Brooks} {Roberto {Castro Portela}}
% mysqlsel $mysql_handler {select first_name, last_name from people order by id asc} -flatlist
Karl Bauer James Brooks Roberto {Castro Portela}
В первом случае (-list parameter) команда возвращает список, элементы которого списки. Во втором случае (-flatlist parameter) команда возвращает список, элементы которого идут все вместе.

Что произойдет если использовать команду mysqlsel без третьего параметра? В этом случае результатом работы команды будет число строк, возвращенных запросом:
% mysqlsel $mysql_handler {select first_name, last_name from people order by id asc}
3
 

mysqlexec

С помощью команды mysqlexec можно послать не_select SQL запрос в бд. Если с помощью этой команды вы пошлете select SQL запрос - ошибки не произойдет, но и ничего не будет сделано.

Посмотрим еще раз на предыдущий пример:

% mysqlexec $mysql_handler {delete from people where id=26}
1
% mysqlsel $mysql_handler {select first_name, last_name, phone from people order by id asc} -list
{James Brooks 1093} {Roberto {Castro Portela} 6507}
% mysqlexec $mysql_handler \\
  {insert into people (id, first_name, last_name, phone) values (58, "Carla", "di Bella", 8925)}
1
% mysqlsel $mysql_handler {select first_name, last_name, phone from people order by id asc} -list
{James Brooks 1093} {Carla {di Bella} 8925} {Roberto {Castro Portela} 6507}
Естественно SQL запросы отличные от delete или insert могут быть посланы с помощью этой команды. Например update данных:
% mysqlexec $mysql_handler {update people set phone=3749 where first_name="James"}
1
% mysqlsel $mysql_handler {select first_name, last_name, phone from people order by id asc} -list
{James Brooks 3749} {Carla {di Bella} 8925} {Roberto {Castro Portela} 6507}
Результатом работы команды mysqlexec является число строк, которые были обработаны не_select SQL запросом.

 

mysqlclose

Команда mysqlclose закрывает соединение с бд. Параметром этой команды является MySQL handler соединения, которое мы хотим закрыть.

 

Другие команды библиотеки MySQLTcl

Набор команд библиотеки MySQLTcl не ограничивается рассмотренными выше - есть команды для получения информации о бд, обработки строк для использования в запросах, создания вложенных запросов. Правильным местом для изучения библиотеки MySQLTcl является ее man страница.

 

Ссылки

[1] a slightly skeptical view on John K. Ousterhout and Tcl:
http://www.softpanorama.org/People/Ousterhout/index.shtml

[2] Руководство по регулярным выражениям Tcl:
http://www.mapfree.com/sbf/tcl/book/select/Html/7.html

TclTutor - бесплатное приложение для изучения Tcl:
http://www.msen.com/~clif/TclTutor.html

Документация MySQL в разных форматах ( HTML, PDF... ):
http://www.mysql.com/documentation/index.html

 

Страница отзывов

У каждой заметки есть страница отзывов. На этой странице вы можете оставить свой комментарий или просмотреть комментарии других читателей
 talkback page 

<--, перейти к начальной странице выпуска

Webpages maintained by the LinuxFocus Editor team
© Diego Alberto Arias Prad, FDL
LinuxFocus.org
Translation information:
en --> -- : Diego Alberto Arias Prad <dariapra(at)yahoo.es>
en --> ru: Pukhlyakov Kirill <kirill(at)linuxfocus.org>

2004-04-23, generated by lfparser version 2.43