Tag Archives: Python

Python版 ぴくぴくダウンローダーを作成している夢を見た

完全オープンソースにするか悩みどころですが取りあえずモチベーション維持のためにもちょくちょくソースコードを公開していこうと思います。

単純にダウンロードするなら簡単なんですが、アレもできてコレもできてとなると中々大変なんですよね(汗

GUIを作るのがかなりしんどいので取りあえず、いつも通りCUI版を作ってGUIを上からかぶせる感じで行こうと思います。
実はTideSDKを使う予定だったけど暗礁に乗り上げてます。誰かアドバイスをください。
※ 毎回GUI後付でやってるけどうまく行っている気がしない・・・

今回の目標
・Pythonを触ったことがない人でも処理をおおまかに理解できるよう書く(そもそも自分がPythonド素人)
・Java版の時みたいに糞長いソースコードを力押しで書かない(今後の保守性を再優先)
・Perl版の時みたいに正規表現のスクランブルにしない(あれは黒歴史)

# vi PixivBrowser.py

# -*- coding:utf-8 -*-
#################################################################
#
# Pixivのブラウザエミュレータ
#
#  Pixivの接続情報を保持する
#  UA設定やProxy設定を組み込むかもしれない
# 
# 【制作開始日時】 2014/06/25
# 【   製作者   】 orbit
# 【  動作環境  】 Python 2.7 (Win, Mac, Linuxで動くのが理想)
#
# 【   更新日   】
#    2014/06/25    ログイン処理に関する部分を作成 
#                  seleniumを使うか悩んだがPixivへの負荷を考慮
#
#    2014/06/27    認証を行うメソッドの名前を変更
#
#################################################################
import mechanize

# Pixivのブラウザエミュレータを担当するクラス
class PixivBrowser(object):
  def __init__(self):

    # Pixivのログインページ
    self.loginurl = 'https://www.secure.pixiv.net/login.php'
    # Pixivのユーザーページ
    self.userpage = 'http://www.pixiv.net/mypage.php'

    # ブラウザエミュレータのインスタンス生成
    self.browser = mechanize.Browser()

    # 当然検索エンジンよけを無視
    self.browser.set_handle_robots(False)

  # Pixivの認証を行う
  def auth(self, username, password):
    # ユーザ情報
    self.username = username # ユーザー名
    self.password = password # パスワード

    # ログインページを開く
    self.browser.open(self.loginurl)
    
    # ユーザ名とパスワードを指定してログイン
    self.browser.select_form(nr=1)
    self.browser["pixiv_id"] = self.username
    self.browser[  "pass"  ] = self.password
    self.browser.submit()

    # ログインに成功した確認する
    res = self.browser.response() # レスポンスを受け取る
    url = res.geturl()            # 現在のURLを取得する

    # ログイン後にユーザページにいないのはログイン失敗
    if(url != self.userpage):
      # ログインに失敗した場合はどうしようもないので例外を投げる
      raise PixivBrowserException("login failed. please check you are account.")

    # ログインページのHTMLを取得
    html = self.browser.response().read()

    # 問題なくログインできたらドヤ顔でログインページのHTMLを返す
    return html

  # ブラウザエミュレータを返す
  def getBrowser(self):
    return self.browser

# PixivBrowserのプログラム内で処理継続が不能になったら呼ばれる例外クラス
class PixivBrowserException(Exception):
  def __init__(self, str):
    self.str = str   # strはraise文から受け取る引数

  def __str__(self): # エラーメッセージ
    return '%s' % (self.str)

## 以下、デバッグ用の処理 ##
if __name__ == '__main__':
  pb = PixivBrowser()
  pb.auth('**************', '**************')

# vi PixivSearch.py

# -*- coding:utf-8 -*-
#################################################################
#
# Pixivの絵画(絵・漫画)を検索・ページングするプログラム
#
#  検索で並び順の変更に対応するかもしれない
# 
# 【制作開始日時】 2014/06/27
# 【   製作者   】 orbit
# 【  動作環境  】 Python 2.7 (Win, Mac, Linuxで動くのが理想)
#
# 【   更新日   】
#    2014/06/27    検索とページングを行う部分を作成
#                  絵・漫画・小説の他にうごくイラストをサポート
#
#################################################################

# Pixivの絵画(絵・漫画)を検索するクラス
class PixivSearch(object):
  def __init__(self, browser):
    ## ページ情報 ##
    # Pixivのユーザーページ
    self.userpage = 'http://www.pixiv.net/mypage.php'
    # 検索ページベース
    self.pixibass = 'http://www.pixiv.net'
    
    # 並び順
    self.pagesort = '&order=date_d'
    
    # ページ番号
    self.pagenumb = 1;
    
    ##  ブラウザ  ##
    self.browser   = browser
  
  # 通常の検索(絵・漫画混在) 今回、仕様的に使うか微妙
  def search(self, keyword):
    # 検索キーワード
    self.keyword = keyword
    
    # 検索パラメータをつける
    self.searcurl = self.pixibass + '/search.php?word=' + keyword + self.pagesort + '&p='
    
    # ページ番号を付加して検索ページを開く
    self.browser.open(self.searcurl + str(self.pagenumb))
    
    # 検索結果ページのHTMLを取得
    html = self.browser.response().read()
    
    # 検索結果ページのHTMLを返す
    return html
  
  # 絵の検索
  def searchImage(self, keyword):
    # 検索キーワード
    self.keyword = keyword
    
    # 検索パラメータをつける
    self.searcurl = self.pixibass + '/search.php?word=' + keyword + '&manga=0' + self.pagesort + '&p='
    
    # ページ番号を付加して検索ページを開く
    self.browser.open(self.searcurl + str(self.pagenumb))
    
    # 検索結果ページのHTMLを取得
    html = self.browser.response().read()
    
    # 検索結果ページのHTMLを返す
    return html
  
  # 漫画の検索
  def searchComic(self, keyword):
    # 検索キーワード
    self.keyword = keyword
    
    # 検索パラメータをつける
    self.searcurl = self.pixibass + '/search.php?word=' + keyword + '&manga=1' + self.pagesort + '&p='
    
    # ページ番号を付加して検索ページを開く
    self.browser.open(self.searcurl + str(self.pagenumb))
    
    # 検索結果ページのHTMLを取得
    html = self.browser.response().read()
    
    # 検索結果ページのHTMLを返す
    return html
  
  # うごくイラストの検索
  def searchUgoku(self, keyword):
    # 検索キーワード
    self.keyword = keyword
    
    # 検索パラメータをつける
    self.searcurl = self.pixibass + '/search.php?word=' + keyword + '&type=ugoira' + self.pagesort + '&p='
    
    # ページ番号を付加して検索ページを開く
    self.browser.open(self.searcurl + str(self.pagenumb))
    
    # 検索結果ページのHTMLを取得
    html = self.browser.response().read()
    
    # 検索結果ページのHTMLを返す
    return html
  
  # 小説の検索
  def searchNovel(self, keyword):
    # 検索キーワード
    self.keyword = keyword
    
    # 検索パラメータをつける
    self.searcurl = self.pixibass + '/novel/search.php?s_mode=s_tag&word=' + keyword + self.pagesort + '&p='
    
    # ページ番号を付加して検索ページを開く
    self.browser.open(self.searcurl + str(self.pagenumb))
    
    # 検索結果ページのHTMLを取得
    html = self.browser.response().read()
    
    # 検索結果ページのHTMLを返す
    return html
  
  # ページ番号を前進
  def nextPage(self):
    # ページ番号をインクリメントする
    self.pagenumb = self.pagenumb + 1
    
    # 次のページ番号を返す
    return self.pagenumb
  
  # ページ番号を後進 今回、仕様的に使うか微妙
  def backPage(self):
    # ページ番号をデクリメントする
    self.pagenumb = self.pagenumb - 1
    
    # 次のページ番号を返す
    return self.pagenumb
  
  # 現在のページ番号を得る
  def getPage(self):
    # 現在のページ番号を返す
    return self.pagenumb
  
  # 現在のページ番号を変更する
  def setPage(self, page):
    # ページ番号を書き換える
    self.pagenumb = page
    
    # 現在のページ番号を返す
    return self.pagenumb

# PixivSearchのプログラム内で処理継続が不能になったら呼ばれる例外クラス
class PixivSearchException(Exception):
  def __init__(self, str):
    self.str = str   # strはraise文から受け取る引数

  def __str__(self): # エラーメッセージ
    return '%s' % (self.str)

## 以下、デバッグ用の処理 ##
if __name__ == '__main__':
  from PixivBrowser import *

  pb = PixivBrowser()
  pb.auth('**************', '**************')
  browser = pb.getBrowser()

  ps = PixivSearch(browser)
  #print ps.search("ミク")
  #print ps.searchImage("ミク")
  #print ps.searchComic("ミク")
  #print ps.searchUgoku("ミク")
  #print ps.searchNovel("ミク")
  ps.setPage(100)
  ps.nextPage()
  print ps.search("ミク")

進捗状態
次は検索結果のHTMLを構文解析するクラスと作品ごと情報を保持するクラスを作成する予定
ID検索の部分に入るまでもう少し時間がかかりそうな予感

Python (mechanize + BeautifulSoup) でPixivにログインしてタイトルタグの中身を取得する夢を見た

PythonでPixivにログインしてタイトルタグの中身を取得する夢を見たのでメモしておきます

# -*- coding:utf-8 -*-
import mechanize
import BeautifulSoup

login_page = 'https://www.secure.pixiv.net/login.php'

username = "**************"
password = "**************"

br = mechanize.Browser()
br.set_handle_robots(False)

# ログインページを開く
br.open(login_page)

# ユーザ名とパスワードを指定してログイン
br.select_form(nr=1)
br["pixiv_id"] = username
br[  "pass"  ] = password
br.submit()

# マイページを取得
html = br.response().read()

# スクレイピング
soup = BeautifulSoup.BeautifulSoup(html)
recipe_title = soup.find("title")
print(recipe_title.string)

br.close()

1万円で放射線量を計測して自動でTwitterに投稿する装置を作ろう!

一昔前はこういう装置を作成するのに結構な費用が必要となっておりましたが最近は非常に低価格かつ簡単に実現することができます。そして計測結果は高い精度を期待できます。
今回は難しいハンダ付けやプログラミングをほとんど行わなくても作成できる事を目標とします。

利用するパーツ

Linux組み込みボード Raspberry Pi 3,500円
組み込み用線量計 ポケットガイガー Type 5 6,450円
ジャンパーワイヤー ジャンパーワイヤ オス⇔メス(10本セット) 400円
ジャンパーワイヤー ジャンパーワイヤ オス⇔オス(70本セット) 400円
ブレッドボード ブレッドボード EIC-801 250円
プルアップ抵抗 【CF1/4-22kΩJ】1/4Wカーボン抵抗 22kΩ 赤赤橙金(100本入) 283円
ピンソケット ピンヘッダ(オスL型) 1×40 (40P) 50円
SDカード ADATA ASDH4GCL4-R SDHCカード Class4 4GB 452円
合計 11,785円

※ 状況によっては価格は変動します。
※ 上記の他に、Windows OSをインストールしたパソコン、モニタ、HDMIケーブル、キーボード、マウス、ネット環境、MicroUSBケーブル、半田ゴテ、ハンダ線、こて台、Twitterアカウントが必要となります。

Twitterのディベロッパー登録

こちらのサイトを元にアプリケーションの登録を済ませておいてください。
下記の内容が必要となります。メモしておいてください。
CONSUMER_KEY,CONSUMER_SECRET,ACCESS_TOKEN,ACCESS_TOKEN_SECRET
bot開発物語 その2―アプリケーション登録―
※ 必ずAPI側でRead and Writeの権限を与えておいてください。

Raspberry PiへのOSインストール

以前の記事を参考にしてください。
Raspberry PiでRaspbianを日本語環境で動かそう!

ピンヘッダのハンダ付け

ピンヘッダの列から5本分を折り取りポケットガイガー Type5に差し込んでハンダ付けします。
IMG_1589[1]

Raspberry Piとポケットガイガー Type5の接続

ブレッドボードとジャンパーワイヤーを使用しRaspberry Piとポケットガイガー Type5の接続を行います。

ワイヤーの色とピンの対応表

ジャンパーワイヤー ポケガ RasPi
赤色 VCC 3v3
黒色 GND GND
青色 SIG GPIO 17
黄色 NS GPIO 27

ポケットガイガー Type5とプルアップ用抵抗をブレッドボードに設置しジャンパーワイヤー(オス⇔オス)で接続します。

IMG_1620[1]

IMG_1621[1]

IMG_1622[1]

ブレッドボードとRaspberry Piをジャンパーワイヤー(オス⇔メス)で接続すます。

IMG_1623[1]

IMG_1625[1]

※ 私のRaspberry PiはP5の位置にピンヘッダがハンダ付けされておりますが気にする必要はありません。

Raspberry Piのピン配置はこのようになっております。
Raspberry_Pi_GPIO

全体的に見るとこういう感じになります。
IMG_1627[1]

Raspberry Piへのプログラムインストール

起動とログイン

Raspberry Piとポケットガイガー Type5を接続した状態でRaspberry Piを起動します。
ログイン後コンソールに下記のコマンドを入力してデスクトップを起動してください。
$ sudo startx
※ こうすることにより管理者権限でGUIな操作を行うことができるようになります。
※ Linux初心者向けにGUIで解説しますがコンソールのみで操作できる方はX Windowを起動する必要ありません。

ターミナルの起動

左下メニュー”アクセサリ”→”LXTerminal”を起動してください。
snapshot1

起動に成功すると真っ黒な画面が出てきます。
snapshot2

真っ黒な画面の中に必要なコマンドを入力していきます。
snapshot3

gitコマンドのインストール

“LXTerminal”内に下記のコマンドを1行ずつ実行してください。
※ #以降の文字列を入力してください。
※ 依存パッケージのインストールを求められる事があります。その場合は”Enter”を押してください。
※ 場合によっては非常に時間が掛かる事があります。気長にお待ちください。
# apt-get update
# apt-get upgrade
# apt-get install git

wiringPiライブラリのインストール

“LXTerminal”内に下記のコマンドを1行ずつ実行してください。
# git clone git://git.drogon.net/wiringPi
# cd wiringPi
# git pull origin
# ./build
# cd ../

Rasdiationのインストール

“LXTerminal”内に下記のコマンドを1行ずつ実行してください。
# git clone git://github.com/orsp/Pocket_Rasdiation_Counter.git
# cd Pocket_Rasdiation_Counter
# make
# make install
# cd ../

Rasdiationの動作テスト

“LXTerminal”内に下記のコマンドを実行してください。
# rasdiation -s 17 -n 27 -b -m

下記の様にCPMやuSv/hの値がカウントされた状態で表示されていれば接続とインストールに成功しています。
snapshot4

Raspberry Pi起動時に連動したRasdiationの自動実行の設定

タスクバー左側アイコンより”ファイルマネージャ”を起動します。
snapshot5

ディレクトリパスに”/etc”と指定しその中の”inittab”をダブルクリックします。
snapshot6

ファイルの最後に下記の行を追記し上書き保存します。
alog:2000:respawn:/usr/local/bin/rasdiation -s 17 -n 27 -o /var/lib/rasdiation/rasdiation.fifo
snapshot7

python-tweepyライブラリのインストール

“LXTerminal”を起動してください。
“LXTerminal”内に下記のコマンドを実行してください。
※ 依存パッケージのインストールを求められる事があります。その場合は”Enter”を押してください。
# apt-get install python-tweepy
# easy_install tweepy
※ apt-getのpython-tweepyは古いようなのでこちらから新しいバージョンのpython-tweepyをインストールします。

Twitter自動投稿スクリプトの設置

“LXTerminal”内に下記のコマンドを1行ずつ実行してください。
# mkdir -p /GEIGERCOUNTER/Twitter
# cp Pocket_Rasdiation_Counter/example/twitter_post.py /GEIGERCOUNTER/Twitter/
# chmod 755 /GEIGERCOUNTER/Twitter/twitter_post.py

Twitter自動投稿スクリプトの設定

タスクバー左側アイコンより”ファイルマネージャ”を起動します。
ディレクトリパスに”/GEIGERCOUNTER/Twitter”と指定します。
“twitter_post.py”をダブルクリックで開きます。
snapshot13

“Twitterのディベロッパー登録”で得たパラメータを記述し上書き保存します。
snapshot14

Twitter自動投稿スクリプトの動作テスト

“LXTerminal”を起動してください。
“LXTerminal”内に下記のコマンドを実行してください。
# python /GEIGERCOUNTER/Twitter/twitter_post.py

設定したTwitterアカウントで下記のような内容がツイートされている事を確認してください。
※ 実際の投稿内容の日付や数値は変化します。
2013年03月24日(日) 11時35分 現在の放射線量は CPM:2.964 uSv/h:0.05589(誤差 0.00833) でした。

Twitter自動投稿スクリプトの定期実行の設定

タスクバー左側アイコンより”ファイルマネージャ”を起動します。
ディレクトリパスに”/etc/cron.d”と指定します。
snapshot8

中に空ファイル”twitter_post”を新規作成します。
snapshot9

作成した”twitter_post”をダブルクリックします。
snapshot10

下記の行を記述し上書き保存します。
※ この設定は30分毎に”twitter_post.py”を実行するという意味です。必要に応じて変更してください。
*/30 * * * * root python /GEIGERCOUNTER/Twitter/twitter_post.py
snapshot15

最終動作確認

正常に30分毎に投稿されるかを確認できましたら放射線量自動投稿機の完成です。
正しく設定されていればRaspberry Piを再起動しても自動で放射線量を計測し投稿いたします。

今回、ブレッドボードを使用しましたがユニバーサル基板を使い回路を作成しても良いかもしれません。
必要があればPythonのスクリプトを改造し自分の好みの投稿内容にするのも楽しいでしょうね。

Raspberry PiでAdafruit製LCD(カラーバックライト+ボタン付きシールド)を利用する

Raspberry PiでAdafruit RGB Negative 16×2 LCD+Keypad Kit for Raspberry Pi – を使ったプログラムをAdafruitの公式ライブラリを使い書いてみました。

シールドの組立、ライブラリのインストールや使い方は公式の方をご覧ください。

下記のソースコードはRasbperry Piの時間とインターフェイス毎のIPアドレスをLCDに表示します。

インターフェイス毎のローカルIPアドレスを取得するために”netifaces”ライブラリを使用しております。
$ apt-get install python-netifaces

/LCDディレクトリを作成し公式ライブラリを入れておきます。
$ sudo mkdir /LCD

$ sudo vi /LCD/MENU_LCD.py

#!/usr/bin/env python
from netifaces import interfaces, ifaddresses, AF_INET

from time import sleep
from Adafruit_I2C import Adafruit_I2C
from Adafruit_MCP230xx import Adafruit_MCP230XX
from Adafruit_CharLCDPlate import Adafruit_CharLCDPlate

from IPaddr_LCD import IPaddr_LCD
from DateTime_LCD import DateTime_LCD

import smbus

lcd = Adafruit_CharLCDPlate(busnum = 1)

class MENU_LCD():
    def get_const_list(self):
        const_list   = []

        ip   = IPaddr_LCD()
        time = DateTime_LCD()

        const_list.append(ip)
        const_list.append(time)

        return const_list

    def print_progress(self, sleep_time, message):
        lcd.clear()
        lcd.message(message)
        sleep(sleep_time)
        self.print_lcd()

    def print_lcd(self):
        pointer_id = 0
        push_flag  = 0

        lcd.clear()
        lcd.message("Please Push\nRite/Left Button")

        const_list = self.get_const_list()
        const_list_size = len(const_list) - 1

        while 1:
            if (lcd.buttonPressed(lcd.RIGHT) or lcd.buttonPressed(lcd.LEFT)):
                if (lcd.buttonPressed(lcd.RIGHT)):
                    if (pointer_id < const_list_size):
                        pointer_id += 1
                    else:
                        pointer_id = 0

                if (lcd.buttonPressed(lcd.LEFT)):
                    if (pointer_id > 0):
                        pointer_id -= 1
                    else:
                        pointer_id = const_list_size

                push_flag  = 1
                const_list[pointer_id].title()

            if (push_flag > 0 and lcd.buttonPressed(lcd.SELECT)):
                const_list[pointer_id].print_lcd()
                break

            if (push_flag > 0 and lcd.buttonPressed(lcd.UP)):
                break

            if (push_flag > 0 and lcd.buttonPressed(lcd.DOWN)):
                break

            sleep(.2)
        return self.print_progress(1, "Reinitializeing\nPlease wate....")

if __name__ == '__main__':
    try:
        menu = MENU_LCD()
        menu.print_progress(3, "Initializeing\nPlease wate....")
        menu.print_lcd()
    except KeyboardInterrupt:
        print("Exit\n")

$ sudo vi /LCD/DateTime_LCD.py

#!/usr/bin/env python
import datetime
import locale

from time import sleep
from Adafruit_I2C import Adafruit_I2C
from Adafruit_MCP230xx import Adafruit_MCP230XX
from Adafruit_CharLCDPlate import Adafruit_CharLCDPlate

import smbus

lcd = Adafruit_CharLCDPlate(busnum = 1)

class DateTime_LCD():
    def title(self):
        lcd.clear()
        lcd.message("Raspberry Pi\nDate Time")
        return

    def print_lcd(self):

        while 1:
            d = datetime.datetime.today()
            time = d.strftime("Date %Y/%m/%d\nTime  %H:%M:%S")

            lcd.clear()
            lcd.message(time)

            if (lcd.buttonPressed(lcd.RIGHT)):
                break

            if (lcd.buttonPressed(lcd.LEFT)):
                break

            sleep(.2)
        return


if __name__ == '__main__':
    try:
        time = DateTime_LCD()
        time.print_lcd()
    except KeyboardInterrupt:
        print("Exit\n")

$ sudo vi /LCD/IPaddr_LCD.py

#!/usr/bin/env python
from netifaces import interfaces, ifaddresses, AF_INET

from time import sleep
from Adafruit_I2C import Adafruit_I2C
from Adafruit_MCP230xx import Adafruit_MCP230XX
from Adafruit_CharLCDPlate import Adafruit_CharLCDPlate

import smbus

lcd = Adafruit_CharLCDPlate(busnum = 1)

class IPaddr_LCD():
    def title(self):
        lcd.clear()
        lcd.message("Raspberry Pi\nIP Address")
        return

    def get_ip_list(self):
        ipaddr_list   = []
        for ifaceName in interfaces():
            nic_ip_list = []
            addresses = [i['addr'] for i in ifaddresses(ifaceName).setdefault(AF_INET, [{'addr':'No IP addr'}] )]
            nic = '%s' % (ifaceName)
            ip  = '%s' % (', '.join(addresses))
            nic_ip_list.append(nic)
            nic_ip_list.append(ip)
            ipaddr_list.append(nic_ip_list)
        return ipaddr_list

    def print_lcd(self):
        pointer_id = 0

        lcd.clear()
        lcd.message("Please Push\nUp/Down Button")

        while 1:
            if (lcd.buttonPressed(lcd.UP) or lcd.buttonPressed(lcd.DOWN)):
                ipaddr_list = self.get_ip_list()
                ipaddr_list_size = len(ipaddr_list) - 1

                if (lcd.buttonPressed(lcd.UP)):
                    if (pointer_id < ipaddr_list_size):
                        pointer_id += 1
                    else:
                        pointer_id = 0

                if (lcd.buttonPressed(lcd.DOWN)):
                    if (pointer_id > 0):
                        pointer_id -= 1
                    else:
                        pointer_id = ipaddr_list_size

                lcd.clear()
                lcd.message(ipaddr_list[pointer_id][0] + "\n" + ipaddr_list[pointer_id][1])

            if (lcd.buttonPressed(lcd.RIGHT)):
                break

            if (lcd.buttonPressed(lcd.LEFT)):
                break

            sleep(.2)
        return

if __name__ == '__main__':
    try:
        ip = IPaddr_LCD()
        ip.print_lcd()
    except KeyboardInterrupt:
        print("Exit\n")

コマンド用の実行ファイルを作成しておきます
$ sudo vi /LCD/LCD_PRINTER

#!/usr/bin/env python
from MENU_LCD import MENU_LCD

if __name__ == '__main__':
    try:
        menu = MENU_LCD()
        menu.print_progress(3, "Initializeing\nPlease wate....")
        menu.print_lcd()
    except KeyboardInterrupt:
        print("Exit\n")

実行権限を与えどこからでもパスが通るように”/usr/bin/”の中にシンボリックを貼っておきます。
$ sudo chmod 700 /LCD/LCD_PRINTER
$ sudo ln -s /LCD/LCD_PRINTER /usr/bin/LCD_PRINTER

せっかくなので起動スクリプトも書いてみました。
$ sudo mkdir /LCD/init.d/
$ sudo vi /LCD/init.d/lcd_printer

#!/bin/sh
### BEGIN INIT INFO
# Provides:          LCD_PRINTER
# chkconfig:         2345 91 91
# Default-Start:     2 3 4 5
# Default-Stop:      0 1 6
# Description:       LCD_PRINTER daemon script.
### END INIT INFO

. /lib/lsb/init-functions

PATH=/sbin:/bin:/usr/sbin:/usr/bin
DAEMON=/usr/bin/LCD_PRINTER
DAEMON_NAME=`basename $DAEMON`
PIDFILE="/var/run/lcd_printer.pid"

set -e

start() {
  log_daemon_msg "Starting $DAEMON_NAME"
  if ! start-stop-daemon --stop --quiet --pidfile ${PIDFILE} --signal 0; then
    start-stop-daemon --start --pidfile ${PIDFILE} --make-pidfile --quiet --background --exec ${DAEMON}
    log_end_msg $?
  else
    echo -n " already running."
    log_end_msg 1
  fi
}

stop() {
  log_daemon_msg "Stopping $DAEMON_NAME"
  start-stop-daemon --stop --pidfile ${PIDFILE}
  log_end_msg $?
}

case "$1" in
  start)
    start
    ;;
  stop)
    stop
    ;;
  restart)
    stop
    start
    ;;
  status)
    status_of_proc -p $PIDFILE $DAEMON $DAEMON_NAME && exit 0 || exit $?
    ;;
  *)
    echo $"Usage: $DAEMONNAME {start|stop|restart|status}" >&2
    exit 1
    ;;
esac
exit 0

実行権限を与え、起動スクリプトとして”/etc/init.d/”の中にシンボリックを貼っておきます。
$ sudo chmod 755 /LCD/init.d/lcd_printer
$ sudo ln -s /LCD/init.d/lcd_printer /etc/init.d/lcd_printer

起動するか確認してみます。
$ sudo service lcd_printer start

自動起動するように設定します。
$ sudo update-rc.d lcd_printer defaults

自動起動するか確認します。完全に電源を落とすためrebootではなくシャットダウンして電源を入れます。
$ sudo shutdown -h now

余談ですがRedHat系はchkconfigで設定するのですがDebian系は違うのですね・・・勉強になりました。

Raspberry Pi wiringpi WiringPi-Python インストール

GPIOを使うのに標準のライブラリよりも使い勝手のよさそうなライブラリを発見したためこちらを使うことにした。

$ sudo apt-get install git python-dev python-setuptools # 必要なパッケージをインストールする
$ cd /tmp # 当然だが/tmpは再起動すると中身が削除されるため注意する
$ git clone https://github.com/WiringPi/WiringPi-Python.git
$ cd WiringPi-Python
$ git submodule update –init
$ sudo cp WiringPi/wiringPi/*.h /usr/include/ # ヘッダーファイルが無いと怒られるためコピーしておく
$ sudo python setup.py install
$ cd

サンプルコード

#!/usr/bin/env python
# -*- coding:utf-8 -*-

import wiringpi
import time

if __name__ == '__main__':
    io = wiringpi.GPIO(wiringpi.GPIO.WPI_MODE_GPIO)
    io.pinMode(23,io.OUTPUT)
    io.digitalWrite(23,io.HIGH)
    while True:
        io.digitalWrite(23,io.LOW)  # on
        time.sleep(1)
        io.digitalWrite(23,io.HIGH) # off
        time.sleep(1)

参考サイト
Raspberry Pi GPIO with Python (without root) – Sirmc.net
fatal error: wiringPi.h: No such file or directory · Issue #7 · WiringPi/WiringPi-Python · GitHub

CentOS 5.4 Python CGI対応

自分は使うことは無いので触る予定はありませんでしたが利用者が使いたい方もおられるでしょうので一応対応させました。
これはその際のメモです。

# yum install *python*
# ln -s /usr/bin/python /usr/local/bin/python

これで対応します。

Python CGIプログラミング入門
ここの例文を利用させていただいたところ無事動作を確認できました^^

Vine Linux 5.0 Python CGIを使う

色々と足りないのがあるのでインストールします。
※私の環境ではpythonは使える環境にありました。
# apt-get install python
# apt-get install python-devel
# apt-get install python-egenix-mx-base
# apt-get install python-tools
# apt-get install python-setuptools
# apt-get install python-babel
# apt-get install python-genshi
# apt-get install mod_python

基本.htaccessを使わないといけなくなるのでhttpd.confには以下の設定に変更しておく。
# vi /etc/apache2/conf/httpd.conf
AllowOverride NoneをAllowOverride FileInfoへ設定

# service apache2 restart

PythonをCGIで使う場合文字化けのためかshiftがエラーになったのでUTF-8で書きましょう。

hello.pyをcgiとして動かす場合は下記のような設定を.htaccessへ記述する。
AddHandler mod_python .py
PythonHandler hello
PythonDebug On

hello.pyの内容

from mod_python import apache

def handler(req):
  req.content_type = "text/plain"
  req.send_http_header()
  req.write("Hello, World")
  return apache.OK

# end.

毎回スクリプトごとに設定してたら気が狂うので下記のような設定方法もあります。
AddHandler mod_python .py
PythonHandler mod_python.publisher
PythonDebug On

慣れないですね^^;
やっぱりPerlが使いやすいかな・・・・・・