QuerySetをまとめて編集したい時

動機
こういう書き方するとSQL沢山発行されるし、長い。

for obj in queryset:
    obj.status = "honyarara"
    obj.save()

そして、書き方をよく忘れるのでメモっておく。


やり方
https://docs.djangoproject.com/en/dev/topics/db/queries/#updating-multiple-objects-at-once
ここに書いてあるけど、一応コード書く。

queryset.update(status="honyarara")

当然、全部のinstanceのstatusがhonyararaになるので注意。
もし、このやり方で場合分けしたい場合はfilterの部分で工夫してそれぞれに対してupdateを使うのがよさそう。

JSで動的にDOMを生成するページをPythonで開く

動機
とあるサイトをスクレイピングしようと思い、おもむろにurllib2を使って下記のように開いてみたところ
明らかに中身のDOMの量が少なかったのです。

import urllib2
response = urllib2.urlopen("http://test.com")
response.read() # 確認すると中身が少ない。悲しい

実際のサイトのソースを覗くと、明らかにurllib2で返ってきたレスポンスと異なっていました。
これはjsでDOMを動的に生成してアップエンドしてるパターンのやつですね。
ということで、Pythonでそういったコンテンツを開く時は
ghost.py
これを使います。

インストール
インストールするにはPySlideかPyQtが必要でさらにこの二つを入れるためには
cmakeとgmakeが必要になります。

Macに入れる場合、brewとpipで簡単に入ります。

brew install cmake
brew install qmake
brew install qt4
pip install PySide
pip install Ghost.py

CentOS6.6でも入れました。

yum install cmake
yum install --enablerepo=atrpms-testing qt47-webkit-devel
yum install libxcb libxcb-devel xcb-util xcb-util-devel
yum install flex bison gperf libicu-devel libxslt-devel ruby
yum install libXrender-devel
wget http://download.qt-project.org/official_releases/qt/4.8/4.8.6/qt-everywhere-opensource-src-4.8.6.tar.gz
yum install libX11-devel mesa-libGL-devel perl-Time-HiRes libxext-dev
tar xzvf qt-everywhere-opensource-src-4.8.6.tar.gz
cd qt-everywhere-opensource-src-4.8.6
./configure
gmake
qmake install
ln -s /usr/local/Trolltech/Qt-4.8.6/bin/qmake /usr/bin/qmake
pip install PySide
pip install Ghost.py

こんな感じ。qmake installでめちゃくちゃ時間かかりました。

使い方

こんな感じですぐに使えます。

from ghost import Ghost
ghost = Ghost()
page, resources = ghost.open("http://www.thisav.com/")
page.content #これで、HTMLが取得出来る。

セキュリティのお勉強

背景

最近Web・サーバーのセキュリティ関係への興味がでてきました。というのも、自分でVPSを借りてずさんな管理体制の中で運用していると雨霰と攻撃が降り注いできます。今までフレームワークやら知識のある人に助けられていたものから、はみ出た途端に露呈する知識のなさ。勉強せず危険性を認識しているのといないのとでは、意識に大きく差が出るはず。ささ、勉強の時間です。

読む教材・読んでる教材

今半分くらい読んでいますが脆弱性の起こる原因から対処法、よくある攻撃手法を実際のコード(PHPベース)で解説していてとても分かりやすいです。
こういう値はエスケープしないと不味いよね、という勘所とその具体的な対応策がケース別に載っているので自分が開発しているものと照らし合わせて考えやすいのもありがたいです。とてもよいよい

Linuxセキュリティ標準教科書(Ver1.0.0)

こちらはありがたいことに無料で読めるセキュリティの教科書でございます。ありがてえありがてえ。
まだ目次を読んでるくらいですが、iptablesの設定やらセキュリティのチェック項目などがあってこちらも実際の運用時に役立ちそうです。
ありがたやありがたや。

まとめ

ちょっとずつ知識をアップグレードしていかなくてはいけないのです。何よりもって、
SQLインジェクション対策もれの責任を開発会社に問う判決 | 徳丸浩の日記
こういう記事を読むとより一層がんばらねばという感じに・・・!

おやじ×メガネ

タイトルの通りのゲームをただいま製作中です。
正確に言うと、開発は一通り終わっていて申請するところです。
こんな感じに、サービス紹介もしております。

http://www.mokukindou.net/corp/oyajimegane.html

メガネを探しているおやじをタッチして、おやじにメガネの場所を教えてあげるだけの
超シンプルなゲームです。tmlib.jsでプロトタイプを作成し、cocos2dで書きなおすという開発スタイルをとりました。この辺りはまたまとめたいと思います。

tmlib.jsで作ったソースはQiitaとかで公開しようかな?

L-99 の一問目を解いてみた

(define my-last
    (lambda (lis)
        (if (null? lis) #f
            (if (null? (cdr lis))
                (car lis)
            (my-last (cdr lis))))))

入れ子のリスト考えなくていいのかな?
と思ったけど、リストの中身が入れ子だろうが最後の要素は最後の要素なのですね

'(a b c '(1 2 3))

最後の要素は '(1 2 3) うん、当たり前のことなのにちょっと考えてしまった。

親クラスの__init__に渡す引数と、子クラスで使う引数を変えたい場合

タイトルのような状況は、DjangoのFormを使っていて起きました。
Formを継承したFormを作成した時に、親のFormの__init__を呼び出す必要があったのですが、親のFormにそのまま余計な引数を渡すと親FormにはKeyErrorが起きるため、余計な引数を__init__を呼ぶ前に除いておく必要がありました。
なので、子のFormにおいて必要な要素と処理をそれぞれfield_nameとprocessingとしたときの例を下に載せておきます。クラス内でも処理の順番によってエラーが出たり上手くいなせたりするんだという当然のことに気づいたので上手く使っていきたいと思います。

class ChildForm(ParentForm):
    def __init__(self, *args, **kwargs):
        if kwargs.get('field_name', None):
            processing(kwargs['field_name'])
            kwargs.pop('field_name')
        super(ChildForm, self).__init__(*args, **kwargs)

変数について

変数について、授業や必要に迫られて初めてプログラムを学び始めた人向けにつらつらと書いてみる。動機としては、授業で突っかかってる友人がいたので、その人が見ることはないだろうけど、自己満足的に。


変数ってデータを入れる箱で変数名はそのラベルだよって説明したけれど、まずその前段階の話から入るべきだった。プログラムは「初めにあるデータ or 入力」をプログラムで操作することで、何らかの「欲しい形のデータ」にして出力するという流れになっている。

だから、データや入力が必ずどこかにあると考えて欲しい。自分でキーボードから文字のデータを入力するにせよ、ファイルからデータを読み込むにせよいずれにしろだ。

そんな時、データをそのままの形で扱うのは非効率になるんだ。

"文字列データです"
#上のような文字列のデータがあったとして

print("文字列データです")
#これはまだいい。

#けれど、この文字列データを別のところでも使わなきゃいけないとき

print("文字列データです")
uppercase("文字列データです")

#こんな風に毎度毎度文字を書かなきゃいけなくなる

上記のようなことをやるのはすごく非効率だ。だから、変数があるんだ。
変数は、データに名前をつけてプログラムに覚えておいてもらうことのできる仕組みだ。

だから、さっきの例文も

data = "文字列データです"

print(data)
uppercase(data)

こんな感じですごく簡潔に書ける。さらに言うと、変数の中にはどんなデータも代入できる。イメージで言えば、段ボールに「A」とでも書いてデータを入れてような感じだ。こうすると、プログラムにはAをどうこうしてくれ、というだけで良いんだ。Aの中身を気にする必要がなくなる。"こーーーーーーーーーーーーーーーーーーーーーーーーーーーーーーーんなに長い文字列も"変数Aに代入するだけで、Aという名前で扱うことが出来るんだ。

うーん…あんまり上手いこと解説出来た気がしないなあ。とにかく、本当のところのアドバイスは、今学んでいる言語で変数の宣言を色々やってみることじゃないだろうか。間違っていそうな書き方をしてみたり、とにかく色々試してみる。絶対すぐにわかるはず、解説聞いているより、よっぽど身になると思う。そんなどうしようもない結論で今日は終わり。プログラム書くのに既に苦手意識もってしまっていたら、すごく申し訳ないなあ、なんて