不少中間件都會用到lua。mysqlproxy,redis,nginx, lua 一高性能著稱。使用腳本能夠大大擴展服務器的功能。Nginx不會自然支持lua. 須要先安裝nginx的模塊lua-nginx-module-0.10.8 。mysql
我有一個應用是用到nginx下載文件。在下載以前會判斷用戶請求是否合法。若是隻是判斷URI地址。僅僅使用nginx的if else 就夠了。可是若是要判斷請求的參數作業務判斷。好比我要拿到用戶傳過來的參數去 調另一個接口校驗,成功則下載。nginx
rewrite_by_lua ' resp=ngx.location.capture("/auth"); ';
這個auth 是個人一個子請求。正則表達式
location =/auth { proxy_pass http://host/api/auth proxy_pass_request_body off; proxy_set_header N-Original-URI $request_uri; proxy_set_header Accept-Encoding ''; }
這裏須要設置一個頭部 proxy_set_header Accept-Encoding ''。不然請求接口返回的數據多是gzip壓縮過的。還要設置N-Original-URI由於接口須要經過N-Original-URI 拿到源地址。redis
首先我必須的判斷請求接口成功與否。sql
if( res.status ~=200 ) then ngx.exit(res.status); end;
若是響應的狀態碼不是200就直接終止本次請求,也不執行下面的lua。執行ngx.exit()的時候把具體錯誤做爲參數傳給它。用戶在頁面上就能夠看到錯誤類型。apache
而後我必須的校驗返回的結果是不是合法的,是否符合基本的正則表達式。不能讓亂七八糟的返回結果向下執行。api
local mbody,merror=ngx,re.match(res.body,"([0-9a-zA-Z]+/)*[0-9a-zA-Z]+"); if(mbody) ngx.var.userkey=mbody[0] else ngx.log(ngx.ERR,"auth chech fail"..(res.body)); ngx.exit(ngx.HTTP_FORBIDDEN); end;
校驗返回的結果是不是 單詞/單詞的形式。lua自己%w能夠表示單詞,可是我在這裏寫%w好像不經過。服務器
若是校驗失敗就打印一個錯誤日誌而後直接終止當前請求。若是成功拿到的變量userkey就能夠作後面請求的地址拼接 proxy_pass http://host/${userkey};性能