djangoのquerysetを任意の順番でsortする
djangoのquerysetを任意の順番でsortする # djnagoではorder_by('hoge')とするとhogeの昇順でならんでいくことは当たり前のように知っているよね。
が、ぼくがやりたかったのは、任意の値でのソート。
databaseに定義されてない値でソートしたかったのです。
とても参考になったstack overflowはこちら。
Django order_by specific order - Stack Overflow
ただしdjango >= 1.8です
TL;DR # from djnago.db.models import Case, When, Value, FloatField # { pid: specific_value, } specific_values = { '1': 100.0, '2': 50.0, '3': 25.0, '4': 123.4, '5': 599.33, } # sqlのCASE式にしたい条件のリスト cases = [] # casesにCASE式にしたい条件をつめていく for pid, specific_value in specific_values.items(): cases.append(When(id=pid, then=Value(specific_value))) # Hogeモデルに対して、pidで絞り込んだあとにcasesをつかってspecific_valueについて注釈づけてorder_byする Hoge.objects.filter(id__in=specific_values.keys()).annotate(specific_value=Case( *cases, output_field=FloatField() )).order_by(specific_value) 詳しい説明 # Conditional Expressions | Django documentation | Django
Djangoでどうしても非同期でコマンドを実行したくなった
経緯 # あるサイトで、顧客に新情報をメールでお知らせしたいときに、今まではコマンド叩いて送信していたのですが、結構面倒なのでブラウザからできないものかと試行錯誤していたのです。
コマンドの設計見直せっていうのは今回は置いといてください・・・。
どうしたのか # いくつかの方法を試しました。
pythonからコマンドを叩く # まず思い浮かんだのがコマンドをnohup &でpythonから叩く。
import subprocess import shlex cmd = 'nohup sleep 10 &' subprocess.Popen(cmd) が!!! レスポンスが帰ってくるのは10秒後・・・。
つぎ!
thread化して逃げる # この前書いたような感じです。
pythonでtupleをつくる - わいがかいた
結局、レスポンスが帰ってくるのは10秒後・・・。 ここ工夫するとどうにかなるような気もする。
つぎ!!
celeryを使う # Celery - Distributed Task Queue — Celery 4.0.2 documentation
ようやく本題。
ググり始めた当初から名前を見かけてはいましたが敷居が高そうなのでスルーしてました。
実際やりはじめて少し後悔しましたし。
結構面倒くさかったので備忘録代わりに。
install # まずは本体をインストールしていきます。
pip install -U Celery
celeryはbrokerとして
Redis RabbitMQ Amazon SQS などを使うことができます。 今回はRedisを選択しました。
yum install redis
bundleも用意されているのでそれも。
pip install -U "celery[redis]"