« 2014年7月 | トップページ | 2014年9月 »

2014年8月の5件の記事

2014-08-30

PythonでKInterbasDBを使ってFirebirdデータベースに接続してみる

KInterbasDBのダウンロード / インストール

Windowsは7と8で両方とも64bitです。Pythonバージョンは2.7なのでkinterbasdb-3.3.0.win-amd64-py2.7.msiをダウンロードしてインストール。

Linuxはkinterbasdb-3.3.0.tar.bz2をインストールしました。

tar xzvf kinterbasdb-3.3.0.tar.bz2
cd kinterbasdb-3.3.0
python setup.py install

接続テスト

古いLinux機を使っているため文字コードがEUC-JPです。
また、使用しているfirebirdは1.5です。
pythonのバージョンは2.4です。

Windows 7と8.1の64bitでも、同じような方法で接続できました。
Python2.7firebird 2.1です。

# -*- coding: euc-jp -*-

import site
import kinterbasdb

def test_conn():
    con = kinterbasdb.connect(dsn='127.0.0.1:/var/gdb/test.gdb',
                              user='sysdba',
                              password='masterkey')
    cur = con.cursor()
    cur.execute('SELECT FIRST 20 ID, TITLE FROM TEST_TBL ORDER BY ID DESC')
    rows = cur.fetchall()
    for (id, title) in rows:
        print '%d\t%s' % (id, unicode(title, 'euc-jp'))
        # Windowsなどでは以下の
        # print '%d\t%s' % (id, unicode(title))
        # で動くと思う
    cur.close()
    con.close()

if __name__ == '__main__':
    test_conn()

14行目の出力の部分は、データベースに格納されているデータの文字コードとの関係があると思います。私の環境ではunicode(titie)ではエラーが出てしまったので、'euc-jp'を渡していますが、Windows環境でデータの文字コードをUNICODE_FSSに指定した環境ではunicode(title)だけで正常に出力してくれました。

レコードをフィールド名と値のディクショナリで取得する

ディクショナリで取得するにはfetchallmap()など、fetch*メソッドにmapをつけるとディクショナリで取得できるようです。実際にやってみました。

# -*- coding: euc-jp -*-

import site
import kinterbasdb

def test_conn():
    con = kinterbasdb.connect(dsn='127.0.0.1:/var/gdb/test.gdb',
                              user='sysdba',
                              password='masterkey')
    cur = con.cursor()
    cur.execute('SELECT FIRST 20 ID, TITLE FROM TEST_TBL ORDER BY ID DESC')
    rows = cur.fetchallmap()
    for fields in rows:
        print '%d\t%s' % (fields["id"], unicode(fields["title"], 'euc-jp'))
        # Windowsなどでは以下の
        # print '%d\t%s' % (id, unicode(title))
        # で動くと思う
    cur.close()
    con.close()

if __name__ == '__main__':
    test_conn()


| | コメント (0) | トラックバック (0)

pythonでMySQL Connectorを使ってデータベースに接続してみる

MySQLに接続してみました。

MySQL connector/Pythonのダウンロード

まずはMySQLのサイトからPython用のコネクターをダウンロードします。

MySQL connector/Pythonのインストール

Windows版はWindowsインストーラで配布されているので、インストーラでインストールするだけだと思います。私は古いLinuxにインストールしたかったのですが、Ubuntu, Debian, SUSE, Red Hatのどのディストリビューションでもないので、Platform Independentを選択してtar.gz形式からインストールしました。

tar xzvf mysql-connector-python-1.0.12.tar.gz
cd mysql-connector-python-1.0.12/mysql-connector-python-1.0.12
python setup.py install

という感じでtarファイルを展開して、setup.pyファイルをinstallパラメータ付きで実行してインストールしました。ファイル/フォルダ名のバージョン番号は利用するバージョンによって変わってくると思います。私の環境ではpythonのバージョンが2.4なので敢えて古いバージョンを選択しました。
Windowsにはpython2.7をインストールしてコネクターは1.2.3をインストーラでインストールしました。

WindowsやUbuntuで利用するなら特に悩むこともなくインストールできるのだと思います。

接続テスト

さっそく、キチンとインストールできたのか、MySQLにアクセスできるかをテストしてみました。

古いLinux機でやったため、システムもデータベースも文字コードがEUC-JPなので文字コードに関する処理の部分が最近の一般的なシステムとはちょっと違ってると思いますので、適宜UTF-8やUnicodeでの処理に置き換えて下さい。

# -*- coding: euc-jp -*-

import site
import mysql.connector

def test_con():
    connect = mysql.connector.connect(user='root', 
                                          password='passwd', 
                                          host = '127.0.0.1', 
                                          database='TestDB', 
                                          charset='ujis')
    cursor = connect.cursor()
    cursor.execute('SELECT ID, TITLE FROM TEST_TBL ORDER BY ID DESC LIMIT 5')
    rows = cursor.fetchall()
    for (id, title) in rows:
        print '%d\t%s' % (id, unicode(title))
    cursor.close()
    connect.close()

if __name__ == "__main__":
    test_con()

14行目のrowsにはタプルが格納されたリストとして返されるようで、リストの1要素が1レコードで、タプルの1要素が1フィールドに対応しているようです。

レコードの内容をディクショナリで取得する

調べてみたら、どうやらMySQL connectorのDevelopment Releasesとなるバージョン2.0.0からはコネクターからカーソルを取得する時にdictionary=Trueとする事でディクショナリのリストとして結果を取得できるようです。

    connect = mysql.connector.connect(user='root', 
                                          password='passwd', 
                                          host = '127.0.0.1', 
                                          database='TestDB', 
                                          charset='ujis')
    cursor = connect.cursor(dictionary = True)
    cursor.execute('SELECT ID, TITLE FROM TEST_TBL ORDER BY ID DESC LIMIT 5')
    rows = cursor.fetchall()
    for fields in rows:
        print '%d\t%s' % (fields["ID"], unicode(fields["TITLE"]))
    cursor.close()
    connect.close()

こんな感じになるんでしょうかね。試してませんのであしからず。

フィールド名と値のディクショナリになってると、SQLの内容やフィールドの順序を知らなくても、フィールド名で値にアクセスできるので便利です。

MySQL for Python

今回テストしたモジュールではないMySQL接続モジュールです。もしかするとこちらのモジュールを使われている方の方が多いのかな。

MySQL for Python ( http://sourceforge.net/projects/mysql-python/ )


続きを読む "pythonでMySQL Connectorを使ってデータベースに接続してみる"

| | コメント (2) | トラックバック (0)

2014-08-28

Authentication with old (insecure) passwords is not supported. For more information, lookup Password Hashing in the latest MySQL manual

せっかく始めたので、データベースにアクセスしたいとMySQL connector Pythonを使ってみた。

Authentication with old (insecure) passwords is not supported. For more information, lookup Password Hashing in the latest MySQL manual

随分古いLinuxでもWindows 8.1でも2台のサーバーのMySQLに接続できているのに、同じソースで何故か一台のコンピュータからだけ接続できずに上記のようなエラーが出ていた。

サポートされていないって言われても、別のクライアントからは同じバージョンのツールでアクセスできてるんだから、できないってことは無いでしょうがよ!

で、結論から書くと一台のサーバーだけ、なぜかHost指定でユーザーが登録されており、そのIPがたまたま今回接続しようとしているコンピュータのIPだった。クライアント側はDHCPからアドレスを取得しているので、本当にたまたまだった訳で、なぜこのホストからだけのユーザーを登録したのかも全然わからないのだが、多分、サーバーを稼働し始めた当時に色々と実験をしていた物が残っていたのだと思う。

他のコンピュータからは同じデータベースに同じユーザー名とパスワードでアクセスできるのに、どうしてかと散々悩んだが、最初からサーバー側を確認すればよかった。クライアント側だけでどうにかできんもんかと悩んでしまった。

まぁ、MySQLとFirebirdにアクセスできれば、自分としてはかなり便利に使えるのでありがたい。

| | コメント (0) | トラックバック (0)

2014-08-26

QpytonでKivyを使ってGUIアプリのサンプルを書いてみた

Androidで動作するPythonQPythonを使ってみました。
Python自体、始めて3日位なので…。

import kivy

from kivy.app import App
from kivy.uix.label import Label
from kivy.uix.button import Button
from kivy.uix.boxlayout import BoxLayout

class MyApp(App):
    def exit_wnd(self, *args):
        App.stop(self)

    def build(self):
        layout = BoxLayout(padding=10,orientation="vertical")
        exit_btn = Button(text = 'exit')
        exit_btn.bind(on_press=self.exit_wnd)
        layout.add_widget(Label(text = 'Hello, World'))
        layout.add_widget(exit_btn)
        return layout

if __name__ == '__main__':
    MyApp().run()

1408998460678.jpg

1408998187862.jpg

イベントハンドラのexit_wndに渡してる*argsがどう使われるのか、いまいち理解してないけど…。

続きを読む "QpytonでKivyを使ってGUIアプリのサンプルを書いてみた"

| | コメント (0) | トラックバック (0)

2014-08-25

pythonで二つの変数の値を交換(swap)する

最近、なんとなくリフレッシュしようと前から興味のあったpythonをいじってみました。

で、swap関数が標準であるのかどうかもわからず、自作しようかと思ったのですが、参照渡しの方法がわからず、調べてみるとpythonには参照渡しが無いとのこと。

で、複数の値の代入ができることを学びました。リストとして扱っているのでしょうかね。

なので、ブログに書くまでのこともなく、簡単に交換できるのですが、自分用の覚書として書いておきます。

a = 10
b = 99

a, b = b, a

print a # 99を出力
print b # 10を出力
となるようです。
def gcd(a, b):
    while a != b:
        if b > a:
            a, b = b, a
        a -= b
    return a

if __name__ == "__main__":
    print gcd(72, 16)

とかで、いいっぽいです。

実行してみるときちんと8が出力されました。

> python gcd.py
8

| | コメント (0) | トラックバック (0)

« 2014年7月 | トップページ | 2014年9月 »