星期三, 8月 25, 2010

一定要自己踢過一次鐵板才能學會 (二)

經過一夜的蒐集資料, 看了Google I/O的影片, 覺得用MapReduce就是正解啦.

用法很簡單
Step 1
Download最新的MapReduce, 在local自己的appengine程式的地方執行.

svn checkout http://appengine-mapreduce.googlecode.com/svn/trunk/python/src/mapreduce
Step 2
修改app.yaml, 固定都是加上下列這段code.

- url: /mapreduce(/.*)?
  script: mapreduce/main.py
  login: admin
Step 3
新增一個mapreduce.yaml檔

mapreduce:
- name: Count the number of entities
  mapper:
    input_reader: mapreduce.input_readers.DatastoreInputReader
    handler: jobs.process
    params:
    - name: entity_kind
      default: main.Report
  • 第一個name, 就是之後會顯示在mapreduce的網頁介面上的job name.
  • input_reader, 目前有四種reader可以選, 詳情可見這裡. 主要是從DataStore裡抓, 或是從BlobStore裡抓, 或是從zip檔裡抓資料.
  • handler, 指定之後會被MapReduce call的function. 這裡有點tricky, 文件寫得不是很清楚, 查了MapReduce的source才知道要填什麼. 簡單的說它可以吃三四種格式, 會試著用不同的方法去找到對應的python檔, class定義跟function定義. 最簡單的方法就是"file.function". 像這裡就是有一個叫jobs.py的檔, 裡面有一個process(). 之後MapReduce就會一直重覆地呼叫這個function.
  • param, 這裡可以指定一些參數, 最重要的是entity_kind這個欄位, 這裡指定了預設值是main.py裡定義的Report model. 之後MapReduce每次call jobs.py裡的process function時, 給他的參數就是Report model裡的其中一個entity. 如此不斷重覆, 直到把Report model裡的所有entity都走過一遍.
Step 4
寫一個job.py

from mapreduce import operation as op
from main import Report

def process(report):
  yield op.counters.Increment("total")

Step 5
上傳到appengine後, 在網頁上看MapReduce的操作介面. 連到自己的網址http://xxxx.appspot.com/mapreduce, 長相會這樣.


在Launch jobs那裡, 會看到剛才在mapreduce.yaml裡指定的mapper名. 下面entity_kind可以看到我們設的預設值, main.Report. 接下Run就會開始執行.

Step 6

這就是結果了, 在右上角可以看到Counter的值是882. 代表Report model總共有882個entities. 用這個方法, 我就可以做其它更細部的統計了.

沒有留言: