diff --git a/Docs/Scripting.md b/Docs/Scripting.md new file mode 100644 index 000000000..b5910d901 --- /dev/null +++ b/Docs/Scripting.md @@ -0,0 +1,59 @@ +Scripting +=== + +Basic [Lua scripting](http://redis.io/commands/EVAL) is supported by the `IServer.ScriptLoad(Async)`, `IServer.ScriptExists(Async)`, `IServer.ScriptExists(Async)`, `IDatabase.ScriptEvaluate`, and `IDatabaseAsync.ScriptEvaluateAsync` methods. +These methods expose the basic commands neccessary to submit and execute Lua scripts to redis. + +More sophisticated scripting is available through the `LuaScript` class. The `LuaScript` class makes it simpler to prepare and submit parameters along with a script, as well as allowing you to use +cleaner variables names. + +An example use of the `LuaScript`: + +``` + const string Script = "redis.call('set', @key, @value)"; + + using (ConnectionMultiplexer conn = /* init code */) + { + var db = conn.GetDatabase(0); + + var prepared = LuaScript.Prepare(Script); + db.ScriptEvaluate(prepared, new { key = (RedisKey)"mykey", value = 123 }); + } +``` + +The `LuaScript` class rewrites variables in scripts of the form `@myVar` into the appropriate `ARGV[someIndex]` required by redis. If the +parameter passed is of type `RedisKey` it will be sent as part of the `KEYS` collection automatically. + +Any object that exposes field or property members with the same name as @-prefixed variables in the Lua script can be used as a paramter hash to +`Evaluate` calls. Supported member types are the following: + + - int(?) + - long(?) + - double(?) + - string + - byte[] + - bool(?) + - RedisKey + - RedisValue + + +To avoid retransmitting the Lua script to redis each time it is evaluated, `LuaScript` objects can be converted into `LoadedLuaScript`s via `LuaScript.Load(IServer)`. +`LoadedLuaScripts` are evaluated with the [`EVALSHA`](http://redis.io/commands/evalsha), and referred to by hash. + +An example use of `LoadedLuaScript`: + +``` + const string Script = "redis.call('set', @key, @value)"; + + using (ConnectionMultiplexer conn = /* init code */) + { + var db = conn.GetDatabase(0); + var server = conn.GetServer(/* appropriate parameters*/); + + var prepared = LuaScript.Prepare(Script); + var loaded = prepared.Load(server); + loaded.Evaluate(db, new { key = (RedisKey)"mykey", value = 123 }); + } +``` + +All methods on both `LuaScript` and `LoadedLuaScript` have Async alternatives, and expose the actual script submitted to redis as the `ExecutableScript` property. \ No newline at end of file diff --git a/README.md b/README.md index eff43adf1..b9e9bcbe3 100644 --- a/README.md +++ b/README.md @@ -38,6 +38,8 @@ Documentation - [Events](https://github.com/StackExchange/StackExchange.Redis/blob/master/Docs/Events.md) - the events available for logging / information purposes - [Pub/Sub Message Order](https://github.com/StackExchange/StackExchange.Redis/blob/master/Docs/PubSubOrder.md) - advice on sequential and concurrent processing - [Where are `KEYS` / `SCAN` / `FLUSH*`?](https://github.com/StackExchange/StackExchange.Redis/blob/master/Docs/KeysScan.md) - how to use server-based commands +- [Profiling](https://github.com/StackExchange/StackExchange.Redis/blob/master/Docs/Profiling.md) - profiling interfaces, as well as how to profile in an `async` world +- [Scripting](https://github.com/StackExchange/StackExchange.Redis/blob/master/Docs/Scripting.md) - running Lua scripts with convenient named parameter replacement Questions and Contributions --- @@ -45,4 +47,4 @@ Questions and Contributions If you think you have found a bug or have a feature request, please [report an issue][2], or if appropriate: submit a pull request. If you have a question, feel free to [contact me](https://github.com/mgravell). [1]: http://msdn.microsoft.com/en-us/library/dd460717%28v=vs.110%29.aspx - [2]: https://github.com/StackExchange/StackExchange.Redis/issues?state=open \ No newline at end of file + [2]: https://github.com/StackExchange/StackExchange.Redis/issues?state=open