Учимся работать с semagic.
Инструкции начинающему блоггеру.
Semagic-это программа для ведения записей в блог-сервисах таких как LiveJournal, blogger и др. Несмотря на то, что semagic довольно популярен, внятной документации про то, как им пользоваться я так и не нашёл. Для зубров блоггинга и околокомпьютерных людей отсутствие документации не является препятствием. Другое дело начинающие блоггеры. Для них и предназначена эти заметки.( Читать далее )
- Mood:productive
- Music:Sarah Vaughan - Sophisticated Lady
Три строчки кода - всё работает
(отчёт о разборках с sqlplus и модулем subprocess.)
Модуль subprocess появился в python 2.4 и предоставляет высокоуровневый и многоплатформенный интерфейс к запуску процессов и работе со стандартными потоками. Оказалось что он вполне удовлетворительно работает с sqlplus: можно запускать sqlplus в качестве процесса и передавать во входной поток данные - sql предложения, а потом читать из выходного потока результаты.Заработало не сразу, пришлось немного повозиться с параметрами, но в результатe всё получилось. Причём работает одинаково под Linux и Windows в том числе и с Oracle Instant Client 10. А это собственно сам код:
import sys, os
import subprocess
sql1='''select FILE_ID,SUBSTR(TABLESPACE_NAME,1,12) TABLESPACE_NAME,BYTES/1024/1024 MB,STATUS
from dba_data_files;\n'''
sql2='''select * from all_users;\n'''
#вариант1 - упрощённый
pp = subprocess.Popen("sqlplus sys/syspasww@testdb",shell=True,stdin=su bprocess.PIPE,stdout=subprocess.PIPE)
output=pp.communicate(sql1)
for line in output:
print line
#вариант 2 - пишем во входной поток несколько строк
pp = subprocess.Popen("sqlplus sys/syspasww@testdb",shell=True, stdin=subprocess.PIPE,stdout=subprocess.P IPE)
pp.stdin.write('set linesize 120\n')
pp.stdin.write(sql1)
pp.stdin.write(sql2)
pp.stdin.flush()
lines=pp.communicate()
for line in lines:
print line
sys.exit()
Python - глазами DBA
(Описание модуля cx_Oracle)
boomzoomer-comp
http://boomzoomer-comp.livejournal.com 2003-2007 г.
Содержание
Почему собственно python
Часть I. Выполняем простой запрос- Часть II.Запросы с параметрами
- Часть III.Анонимные блоки PL/SQL
- Ссылки
- Листинги
Почему собственно python
Администраторы БД очень часто нуждаются в инструментах для автоматизации разной рутинной работы, например: загрузка, преобразования данных в разного рода форматы или сбор и анализ различной статистики.Для меня в свое время такой палочкой-выручалочкой стал perl.
Через некоторое время я набрел на python.Вот все что я могу сказать после 1 года знакомства:
Это практичный и полезный инструмент.
Несколько слов об инструментах.Вариантов на самом деле немного: 1)гремучая смесь из разных утилит командной строки (bash+awk+tar+...), 2)языки сценариев(perl,tcl/tk... ), 3)классические языки программирования(С,C++)
Первый вариант наиболее часто применяется администраторами.По крайней мере мой собственный опыт говорит о том, что иногда удается получить неплохое решение, если только задача не слишком сложна.
Третий вариант позволяет получить великолепное решение при значительных затратах сил и времени на программирование,отладку и тестирование кода.А если их нет?
Золотой серединой очевидно является вариант номер 2.
К языкам сценариев по функциональным возможностям приближается java, поскольку фирма Oracle(к моему большому сожалению )взяла главный курс на использование языка java везде,где это только возможно, теперь java работает в контексте ядра Oracle и в принципе может быть использована как инструмент администратора.
Проблемы я вижу следующие:
-слишком сложные API,плохая читабельность кода
-отсутствие встроенных современных типов данных,
- крайняя медлительность выполнения,
-необходимость обновлять программы с Oracle Metalink.
- Java API имеет плохую обратную совместимость с предыдущими версиями
-java -это не собственная разработка Oracle corp., а технология , лицензированная у Sun , которая кое-что лицензировала еще у нескольких фирм.
С perl обычно все намного лучше.Дух открытости (движение Open Source и лицензия GPL) позволил Perl прогрессировать с космической скоростью:
-огромное количество великолепных библиотек,
-встроенные структуры данных-списки,hash-таблицы
-существование многочисленных книг, списков рассылки и просто энтузиастов значительно облегчают жизнь профессионалу.
Несмотря на массу положительных свойств, Perl имеет imho ряд существенных недостатков:
-крайне запутанный и к тому же подверженный изменениям синтаксис.
-значительная интеграция с юниксообразными ОС.
-не очень удачные средства поддержки OOP
Первое затрудняет сопровождение (даже собственных) программ.А второе ограничивает сферу применимости языка на других платформах.
И здесь важно отметить, что разработчики python в значительной степени учли достоинства и недостатки различных языков программирования и в результате появился язык программирования, который почти не содержит в себе экзотических конструкций и позволяет использовать почти все известные на сегодня методы создания программ.
Справедливости ради нужно заметить, что python отнюдь не является чем то уникальным, мне известен еще один язык программирования с похожим функционалом - ruby.Этот язык несколько моложе чем python и для серьезного промышленного применения он еще, похоже не готов.Не все в порядке с документацией и набор библиотек совсем невелик. Ruby довольно популярен среди американских студентов, поэтому, возможно у него впереди яркая судьба.
Достоинства языка python
Python можно охарактеризовать в нескольких словах следующим образом:
многоплатформенный язык сценариев с динамической типизацией,встроенными структурами данных и поддержкой трех парадигм программирования-процедурной,объектной, функциональной.
- Многоплатформенность и масштабируемость-работает на большинстве известных программно-аппаратных платформ от PDA до CRAY и IBM 390
- Гармоничная архитектура языка:
- Простой и удобный для понимания логики програм синтаксис
- Встроенные структуры данных-списки, кортежи,словари
- Огромное количество библиотек:
-XML парсеры
-GUI(Win32,GTK/GNOME,KDE/QT,TK,FOX,WXWindows)
- Сетевые протоколы
- Разработка Web приложений - Переносимость кода между различными платформами
- Мощные интерфейсы к конкретным ОС(особенно к Linux/Unix и win32)
- Поддержка разных стилей программирования-процедурного,объектного,ф
ункционального - Встроенная поддержка Unicode и множества национальных кодировок
(включая 5 русских) - Возможность писать самодокументированные программы и автоматическая генерация документации на модули.
С чем реально сталкивается программист(а админитстратор является таковым часто, но понемногу ) при использовании python.Это простой и ясный синтаксис. Я ловлю себя часто на мысли,что просмотр чужого кода зачастую не требует значительного напряжения.И здесь помогает то, что отступы являются частью синтаксиса и определяют вложенность операторов.
Библиотеки зачастую имеют очень лаконичную документацию, но этого достаточно так как API очень выразительны и внятны. Отрадным явлением в мире питона, является тот факт, что очень многие библиотеки были разработаны после того, как были согласованы спецификации на конкретные API.Одной из таких спецификаций является спецификация на Python Database API 2.0. В соответствии с этой спецификацией разрабатываются модули для доступа к конкретным СУБД.
К сожалению сам стандарт(как в свое время и cпецификация на ODBC) не может учесть все специфические особенности конкретной СУБД, так как фирмы-производители СУБД, используют свои фирменные расширения как средство в конкуретной борьбе. Поэтому перенос кода с одной платформы на другую все-таки очень трудно сделать безболезненным, если только перед разработчиками не ставилась задача писать приложения, предназначенное для работы с различными SQL серверами.
Сам процес кодирования и тестирования достаточно комфортен.Здесь помогает качественная диагностика ошибок.Оттестированные модули очень легко расширять и складывать из них приложения.
Для работы с RDBMS Oracle существует несколько различных модулей для Python, использующих разные механизмы:
- ODBC(Win32,Linux)
- DCOM(Win32)
- PERL_DBI(Win32,Linux,Solaris,HP-UX,AIX)
- NATIVE API (Win32,Linux,Solaris,HP-UX,AIX)
Более подробную информацию Вы можете найти на www.python.org.
Часть I. Выполняем простой запрос.
Я предпочитаю использовать модуль cx_Oracle, который был проверен мною в ОС NT и Linux(автор-Anthony Tuininga утверждает что он работает в Solaris и похоже, на всех юниксообразных ОС должен также работать ).В основном этот модуль следует спецификации Python Database API 2.0 и поддерживает работу с RDBMS Oracle версий 8.1-9.xx.
Модуль написан на языке С, что обеспечивает быструю обработку данных и позволяет использовать все достоинства языка Python.
Для быстрого погружения в предмет я приведу фрагменты кода, демонстрирующего основные приемы использования модуля.
try:
import cx_Oracle
except ImportError,info:
print "Import Error:",info
sys.exit()
if cx_Oracle.version<'3.0':
print "Very old version of cx_Oracle :",cx_Oracle.version
sys.exit()
В этом фрагменте демонстрируется безопасная загрузка модуля cx_Oracle и проверка версии. Надеюсь, элегантность синтаксиса все-таки заметили :-)
Далее создадим экземпляр класса connect, именно этот объект и обеспечивает взаимодействие с сервером Oracle
try:
my_connection=cx_Oracle.connect('system/manager@test_db')
except cx_Oracle.DatabaseError,info:
print "Logon Error:",info
exit(0)
Теперь создаем курсор и выполняем запрос:
my_cursor=my_connection.cursor()
try:
my_cursor.execute("""
SELECT OWNER,SEGMENT_TYPE,TABLESPACE_NAME,SUM(BLOCKS)SIZE_BLOCKS,
COUNT(*) SIZE_EXTENTS FROM DBA_EXTENTS
GROUP BY OWNER,SEGMENT_TYPE,TABLESPACE_NAME
""")
except cx_Oracle.DatabaseError,info:
print "SQL Error:",info
exit(0)
Динамическая типизация и поддержка сложных структур данных позволяет легко обработать результаты SQL запроса. В результате вызова my_cursor.fetchall() возращается список записей,каждая из которых явлеяется кортежем(неизменяемым списком) полей разного типа. Если вы знакомы с PL/SQL, то тогда цикл по списку записей будет очевидным:
for record in my_cursor.fetchall(): <обработка записи record, record содержит кортеж из полей текущей записи>
Существует еще более любопытная возможность "разобрать" текущую запись по полям:
for OWNER,SEGMENT_TYPE,TABLESPACE_NAME,SIZE_BLOCKS,SIZE_EXTENTS in my_cursor.fetchall(): <теперь можно обращаться к переменным, содержащим значения одноименных полей курсора>
Печатаем результат на stdout. Замечу здесь, что my_cursor.description возвращает описание столбцов запроса в виде списка кортежей. Для каждого столбца возвращаются следующие данные:(name, type_code, display_size, internal_size, precision, scale, null_ok). Далее следует форматированный вывод на stdout( почти как printf в языке C).
print
print 'Database:',my_connection.tnsentry
print
print "Used space by owner, object type, tablespace "
print "----------------------------------------------------------------------------------"
title_mask=('%-16s','%-16s','%-16s','%-8s','%-8s')
i=0
for column_description in my_cursor.description:
print title_mask[i]%column_description[0],
i=1+i
print ''
print "----------------------------------------------------------------------------------"
row_mask='%-16s %-16s %-16s %8.0f %8.0f '
for record in my_cursor.fetchall():
print row_mask%record
В результате мы увидим что-то вроде:
Database: testdb Used space by owner, object type, tablespace -------------------------------------------------------------------------------- OWNER SEGMENT_TYPE TABLESPACE_NAME SIZE_BLOCKS SIZE_EXTENTS -------------------------------------------------------------------------------- ADU2 INDEX USERS 784 25 ADU2 TABLE USERS 512 24 ADUGKS INDEX DEVELOP_DATA 984 123 ADUGKS TABLE DEVELOP_DATA 664 83 ADUGPA INDEX USERS 784 25 ADUGPA TABLE USERS 496 23 AGNKS_SG INDEX USERS 352 22 AGNKS_SG TABLE USERS 240 15 ATU INDEX USERS 3968 244 ATU TABLE DEVELOP_DATA 8 1 ATU TABLE USERS 2688 160 ATU1 INDEX DEVELOP_DATA 1600 200 ATU1 INDEX USERS 608 38 ATU1 TABLE DEVELOP_DATA 1032 129 ATU1 TABLE USERS 544 34 BUX INDEX DEVELOP_DATA 64 8 BUX TABLE DEVELOP_DATA 1736 217 DISP INDEX USERS 400 25 DISP TABLE USERS 528 33 EPE INDEX USERS 80 5 EPE TABLE USERS 48 3 EXZ INDEX USERS 1088 61 EXZ TABLE DEVELOP_DATA 8 1 EXZ TABLE USERS 832 41
Часть II. Запросы с параметрами.
Согласно спецификации Python Database API 2.0, для выполнения запросов с параметрами каждый модуль должен реализовывать переменную paramstyle, которая определяет каким образом будут передаваться параметры запросов. Текущая версия cx_Oracle(3.0) поддерживает режим 'named', то есть в модуле установлена переменная cx_Oracle.paramstyle='named' и можно создавать конструкции в запросах в виде:
select * from all_users where USERNAME LIKE :S
При этом связывание параметров запроса со значениями можно можно выполнить двумя способами:
- Именованный параметeр метода execute:
cursor2.execute("select * from all_users where USERNAME LIKE :S ",S='S%') - Словарь {':переменная':значение,...}
cursor2.execute("select * from all_users where USERNAME LIKE :S ",{':S':'S%'})
Часть III. Анонимные блоки PL/SQL
Несмотря на существавания стандартов на язык SQL, реальные потребности администратора часто требуют использования нестандартных средств сервера(более того, написать приложение, работающее с сервером на стандартном SQL возможно только для весьма тривиальных приложений ), для Oracle таким нестандартным, но очень удобным механизмом является возможность исполнения анонимных блоков PL/SQL. Модуль сx_Oracle реализует этот механизм, который естественно не описан в спецификации Python Database API 2.0 .
Чтобы связать переменные блока PL/SQL c переменными языка PYTHON, в модуле сx_Oracle реализован класс var.Эекземпляр можно создать следующим образом:
var=my_cursor.var(cx_Oracle.DATETIME)
Конструктор my_cursor.var(...) в качестве параметра требует указать тип создаваемой переменной. Варианты:
- BINARY
- DATETIME
- FIXEDCHAR
- LONGBINARY
- LONGSTRING
- NUMBER
- ROWID
- STRING
var=my_cursor.var(cx_Oracle.DATETIME)
try:
my_cursor.execute("""begin
SELECT SYSDATE INTO :p_Value from dual;
end;""",p_Value = var)
except cx_Oracle.DatabaseError,info:
print "SQL Error:",info
exit(0)
Очевидно, что теперь var содержит текущее время сервера.Доступ к значениям переменной выполняется с помощью метода var.getvalue():
CDATE=var.getvalue() print 'Date: %02u/%02u/%4u'%(CDATE.day,CDATE.month,CDATE.year) print 'Time: %02u:%02u:%02u'%(CDATE.hour,CDATE.minute,CDATE.second)
Этот пример демонстрирует также и форматирование даты и времени для экземпляра var. В результате напечатается нечто вроде:
Date: 12/05/2003 Time: 16:42:54
Всвязи с тем, что работа с типами времени и даты внутри сервера Oracle реализованы особенным образом ( независимо от ОС), модуль сx_Oracle реализует следующие функции для для преобразования значений дат и времени :
- Date( year, month, day)
- DateFromTicks( ticks)
- Time( hour, minute, second)
- TimeFromTicks( ticks)
- Timestamp( year, month, day, hour, minute, second)
- TimestampFromTicks( ticks)
var=my_cursor.var(cx_Oracle.DATETIME) var.setvalue(0,cx_Oracle.Date( 2002, 02,12)) CDATE=var.getvalue() print 'Date: %02u/%02u/%4u'%(CDATE.day,CDATE.month,CDATE.year) print 'Time: %02u:%02u:%02u'%(CDATE.hour,CDATE.minute,CDATE.second)
Результат будет следующий:
Date: 12/02/2002 Time: 00:00:00
Ссылки
cx_Oracle-Python extension module that allows access to Oracle
Author: Anthony Tuininga http://computronix.com/utilities.shtml
Python Database API specification Python http://www.python.org/topics/database/Da
Листинги
Листинг 1.
Выполняем простой запрос
""
cx_Oracle demo
simple query
"""
__AUTHOR__='http://boomzoomer-comp.livejournal.com '
__COPYRIGHT__='boomzoomer 2003-2007.'_
"""
from sys import exit
try:
import cx_Oracle
except ImportError,info:
print "Import Error:",info
sys.exit()
if cx_Oracle.version<'3.0':
print "Very old version of cx_Oracle :",cx_Oracle.version
sys.exit()
try:
my_connection=cx_Oracle.connect('system/password@mydb')
except cx_Oracle.DatabaseError,info:
print "Logon Error:",info
exit(0)
my_cursor=my_connection.cursor()
try:
my_cursor.execute("""
SELECT OWNER,SEGMENT_TYPE,TABLESPACE_NAME,SUM(BLOCKS)SIZE_BLOCKS,
COUNT(*) SIZE_EXTENTS FROM DBA_EXTENTS
GROUP BY OWNER,SEGMENT_TYPE,TABLESPACE_NAME
""")
except cx_Oracle.DatabaseError,info:
print "SQL Error:",info
exit(0)
print
print 'Database:',my_connection.tnsentry
print
print "Used space by owner, object type, tablespace "
print "-----------------------------------------------------------"
title_mask=('%-16s','%-16s','%-16s','%-8s','%-8s')
i=0
for column_description in my_cursor.description:
print title_mask[i]%column_description[0],
i=1+i
print ''
print "------------------------------------------------------------"
row_mask='%-16s %-16s %-16s %8.0f %8.0f '
for record in my_cursor.fetchall():
print row_mask%record
for column_description in my_cursor.description:
print column_description
Листинг 2.
Запрос с параметрами
""
cx_Oracle demo
query with parameters
"""
__AUTHOR__='http://boomzoomer-comp.livejournal.com '
__COPYRIGHT__='boomzoomer 2003-2007.'
from sys import exit
try:
import cx_Oracle
except ImportError,info:
print "Import Error:",info
sys.exit()
if cx_Oracle.version<'3.0':
print "Very old version of cx_Oracle :",cx_Oracle.version
sys.exit()
try:
my_connection=cx_Oracle.connect('system/manager@test_db')
except cx_Oracle.DatabaseError,info:
print "Logon Error:",info
exit(0)
my_cursor=my_connection.cursor()
try:
my_cursor.execute("""
SELECT OWNER,SEGMENT_TYPE,TABLESPACE_NAME,SUM(BLOCKS)SIZE_BLOCKS,
COUNT(*) SIZE_EXTENTS FROM DBA_EXTENTS
WHERE OWNER LIKE :S
GROUP BY OWNER,SEGMENT_TYPE,TABLESPACE_NAME
""",S='SYS%')
except cx_Oracle.DatabaseError,info:
print "SQL Error:",info
exit(0)
print
print 'Database:',my_connection.tnsentry
print
print "Used space by owner, object type, tablespace "
print "-----------------------------------------------------------"
title_mask=('%-16s','%-16s','%-16s','%-8s','%-8s')
i=0
for column_description in my_cursor.description:
print title_mask[i]%column_description[0],
i=1+i
print ''
print "------------------------------------------------------------"
row_mask='%-16s %-16s %-16s %8.0f %8.0f '
for record in my_cursor.fetchall():
print row_mask%record
© http://boomzoomer-comp.livejournal.com 2003-2007
1 Установка Oracle Instant Client 10.2 -далее OIC
Проверка показала, что OIC v.10.2 нормально работает с серверами версии (8.1.x,9.x и 10.х)
OIC v.11.x c серверами версии 8.1.х не работает вовсе.
с сайта Oracle.com качаем следующие файлы
1) oracle-instantclient-basic-10.2.0.4-1.i3
2) oracle-instantclient-sqlplus-10.2.0.4-1.i
3) oracle-instantclient-devel-10.2.0.4-1.i3
С правами root распаковывем архивы в каталог
/usr/lib/oracle/instantclient при этом первые два архива кладём в корень,
а третий должен лежать в подкаталоге sdk(как он лежит в архиве)
далее в файле /etc/ld.so.conf добавляем строчку
/usr/lib/oracle/instantclient
после чего даём команду
>ldconfig
Теперь система знает где искать библитотеки от OIC. Далее можно попробовать sqlplus в работе и проверить работоспособность клиента.
Поскольку я работю с локалью UTF-8 то делaть это нужно так(локаль для Oracle должна совпадать с локалью вашей сессии):
> NLS_LANG=american_america.utf8 ./sqlplus user/pasword@//hostname/servicename
Если заработало, и русские буквы отображаются нормально, то NLS_LANG
нужно внести в ваш .profile
2. Сборка cx_Oracle -4.3.3
Для того, чтобы собрать cx_Oracle придётся прибегнуть к двум трюкам, к которым я пришёл изучая setup.py
1) При сборке модуля setup.py пытается определить версию OIC путём поиска файла
где xx-номер версии, в дальнейшем этот файл никак не используется. Поэтому создим каталог lib и в него положим пустой файл с именем libclient10.a
2) Для сборки модуля требуется библиотека libclntsh.so, которая в OIC имеет имя файла libclntsh.so.10.1.
Поэтому просто создадим ссылку :
> ln -s libclntsh.so.10.1 libclntsh.so
3) Теперь собственно осталось собрать cx_Oracle
Распаковывем архив и с правами root выдаём
> ORACLE_HOME=/usr/lib/oracle/instantclien
> python ./setup.py install
Generator Tricks for Systems Programmers.
http://www.dabeaz.com/generators/in
Как обычно мастер конкретен и нагляден.
Очень рекомендую
Некоторые полезные факты:
1) Современные архиваторы дают очень хороший коэф. сжатия регулярных данных.
2) Разница в коэф. сжатия между лучшими из них сотавляет считанные проценты.
3) Экстремальные режимы дают мизерный прирост степени сжатия и при этом время архивирования вырастает в 3-4 раза.
Вывод:
1) Для архивирования большого объёма данных можно пользоваться архиваторами 7-zip, rar, или bzip2.
Никакого существенного выигрыша ни один из них не даёт.
2) Не пользоваться настройками для сильного сжатия .
График для сравнения эффективности 7-zip и bzip2
После просмотра десятка мониторов и чтения 2 обзоров с тестами остановился
на Viewsonic VP930-3.
http://www.viewsoniceurope.com/uk/Produc
Первые впечатления.
Дизайн и эргономика-очень хорошо. Подставка металлическая и позволяет легко регулировать положения по 3 осям. Удобно.Дизайн -не броский.
Матрица -MVA.Картинка- выше всяких ожиданий . После калибровки все цвета выглядят достойно и натурально, что является редкостью в наше время в серийных мониторах.
Глазки в общем не напрягяет. Хороший запас по контрасту.
В общем тем, кто бережёт своё зрение и уважает качество изображения - вполне подходящая вещь.
( КРАТКОЕ ОПИСАНИЕ Viewsonic VP930 )
