├── Makefile ├── README.md ├── lapis-redis-dev-1.rockspec └── lapis ├── redis.lua └── redis.moon /Makefile: -------------------------------------------------------------------------------- 1 | test: 2 | busted 3 | 4 | lint: build 5 | moonc -l lapis 6 | 7 | local: build 8 | luarocks --lua-version=5.1 make --local lapis-redis-dev-1.rockspec 9 | 10 | build: 11 | moonc lapis 12 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | 2 | # `lapis-redis` 3 | 4 | This module is used for integrating [Redis](http://redis.io) with 5 | [Lapis](http://leafo.net/lapis). It uses the 6 | [`lua-resty-redis`](https://github.com/openresty/lua-resty-redis) module. 7 | 8 | ## Installing 9 | 10 | ```bash 11 | $ luarocks install lapis-redis 12 | ``` 13 | 14 | ## Configuring 15 | 16 | ```moonscript 17 | -- config.moon 18 | 19 | config "development", -> 20 | redis { 21 | host: "127.0.0.1" 22 | port: 6379 23 | } 24 | 25 | ``` 26 | 27 | ## Connecting 28 | 29 | The function `get_redis` can be used to get the current request's Redis 30 | connection. If there's not connection established for the request a new one 31 | will be opened. After the request completes the Redis connection will 32 | automatically be recycled for future requests. 33 | 34 | The return value of `get_redis` is a connected 35 | [`lua-resty-redis`](https://github.com/openresty/lua-resty-redis#methods) 36 | object. 37 | 38 | ```moon 39 | import get_redis from require "lapis.redis" 40 | 41 | class App extends lapis.Application 42 | "/": => 43 | redis = get_redis! 44 | redis\set "hello", "world" 45 | 46 | redis\get "hello" 47 | ``` 48 | 49 | 50 | ## Redis cache 51 | 52 | You can use Redis as a cache using the [Lapis caching 53 | API](http://leafo.net/lapis/reference/utilities.html#caching-cachedfn_or_tbl). 54 | 55 | ```moon 56 | import cached from require "lapis.cache" 57 | import redis_cache from require "lapis.redis" 58 | 59 | class App extends lapis.Application 60 | "/hello": cached { 61 | dict: redis_cache "cache-prefix" 62 | => 63 | @html -> 64 | div "hello" 65 | } 66 | ``` 67 | 68 | -------------------------------------------------------------------------------- /lapis-redis-dev-1.rockspec: -------------------------------------------------------------------------------- 1 | package = "lapis-redis" 2 | version = "dev-1" 3 | 4 | source = { 5 | url = "git://github.com/leafo/lapis-redis.git" 6 | } 7 | 8 | description = { 9 | summary = "Redis integration with lapis", 10 | license = "MIT", 11 | maintainer = "Leaf Corcoran ", 12 | } 13 | 14 | dependencies = { 15 | "lua == 5.1", 16 | "lapis" 17 | } 18 | 19 | build = { 20 | type = "builtin", 21 | modules = { 22 | ["lapis.redis"] = "lapis/redis.lua", 23 | } 24 | } 25 | 26 | -------------------------------------------------------------------------------- /lapis/redis.lua: -------------------------------------------------------------------------------- 1 | local config = require("lapis.config").get() 2 | local redis 3 | if ngx and ngx.socket then 4 | redis = require("resty.redis") 5 | end 6 | local redis_down = nil 7 | local connect_redis 8 | connect_redis = function() 9 | local redis_config = config.redis 10 | if not (redis_config) then 11 | return nil, "redis not configured" 12 | end 13 | local r = redis:new() 14 | local ok, err = r:connect(redis_config.host, redis_config.port) 15 | if ok then 16 | return r 17 | else 18 | redis_down = ngx.time() 19 | return ok, err 20 | end 21 | end 22 | local get_redis 23 | get_redis = function() 24 | if not (redis) then 25 | return nil, "missing redis library" 26 | end 27 | if redis_down and redis_down + 60 > ngx.time() then 28 | return nil, "redis down" 29 | end 30 | local r = ngx.ctx.redis 31 | if not (r) then 32 | local after_dispatch 33 | after_dispatch = require("lapis.nginx.context").after_dispatch 34 | local err 35 | r, err = connect_redis() 36 | if not (r) then 37 | return nil, err 38 | end 39 | ngx.ctx.redis = r 40 | after_dispatch(function() 41 | r:set_keepalive() 42 | ngx.ctx.redis = nil 43 | end) 44 | end 45 | return r 46 | end 47 | local redis_cache 48 | redis_cache = function(prefix) 49 | return function(req) 50 | local r = get_redis() 51 | return { 52 | get = function(self, key) 53 | if not (r) then 54 | return 55 | end 56 | do 57 | local out = r:get(tostring(prefix) .. ":" .. tostring(key)) 58 | if out == ngx.null then 59 | return nil 60 | end 61 | return out 62 | end 63 | end, 64 | set = function(self, key, content, expire) 65 | if not (r) then 66 | return 67 | end 68 | local r_key = tostring(prefix) .. ":" .. tostring(key) 69 | return r:setex(r_key, expire, content) 70 | end 71 | } 72 | end 73 | end 74 | return { 75 | get_redis = get_redis, 76 | redis_cache = redis_cache 77 | } 78 | -------------------------------------------------------------------------------- /lapis/redis.moon: -------------------------------------------------------------------------------- 1 | config = require"lapis.config".get! 2 | redis = if ngx and ngx.socket 3 | require "resty.redis" 4 | 5 | redis_down = nil 6 | 7 | connect_redis = -> 8 | redis_config = config.redis 9 | return nil, "redis not configured" unless redis_config 10 | 11 | r = redis\new! 12 | ok, err = r\connect redis_config.host, redis_config.port 13 | 14 | if ok 15 | r 16 | else 17 | redis_down = ngx.time! 18 | ok, err 19 | 20 | get_redis = -> 21 | return nil, "missing redis library" unless redis 22 | return nil, "redis down" if redis_down and redis_down + 60 > ngx.time! 23 | 24 | r = ngx.ctx.redis 25 | unless r 26 | import after_dispatch from require "lapis.nginx.context" 27 | 28 | r, err = connect_redis! 29 | return nil, err unless r 30 | 31 | ngx.ctx.redis = r 32 | after_dispatch -> 33 | r\set_keepalive! 34 | ngx.ctx.redis = nil 35 | 36 | r 37 | 38 | redis_cache = (prefix) -> 39 | (req) -> 40 | r = get_redis! 41 | 42 | { 43 | get: (key) => 44 | return unless r 45 | with out = r\get "#{prefix}:#{key}" 46 | return nil if out == ngx.null 47 | 48 | set: (key, content, expire) => 49 | return unless r 50 | r_key = "#{prefix}:#{key}" 51 | r\setex r_key, expire, content 52 | 53 | } 54 | 55 | 56 | { :get_redis, :redis_cache } 57 | 58 | --------------------------------------------------------------------------------