From eb5255939f893a5e35981e25d9ca4244eea55f5e Mon Sep 17 00:00:00 2001 From: "Dmitry E. Oboukhov" <unera@debian.org> Date: Tue, 21 Aug 2012 13:07:12 +0400 Subject: [PATCH] box.uuid() and box.uuid_hex() functions https://blueprints.launchpad.net/tarantool/+spec/box-uuid --- doc/user/stored-procedures.xml | 32 ++++++++++++++++ mod/box/CMakeLists.txt | 3 +- mod/box/box_lua.m | 4 ++ mod/box/box_lua_uuid.h | 9 +++++ mod/box/box_lua_uuid.m | 67 ++++++++++++++++++++++++++++++++++ test/box/lua.result | 13 +++++++ test/box/lua.test | 6 +++ 7 files changed, 133 insertions(+), 1 deletion(-) create mode 100644 mod/box/box_lua_uuid.h create mode 100644 mod/box/box_lua_uuid.m diff --git a/doc/user/stored-procedures.xml b/doc/user/stored-procedures.xml index 2e6ce5636c..f022711a1c 100644 --- a/doc/user/stored-procedures.xml +++ b/doc/user/stored-procedures.xml @@ -726,6 +726,38 @@ lua box.dostring('local f = function(key) t=box.select(0, 0, key); if t ~= nil t </para> </listitem> </varlistentry> + <varlistentry> + <term> + <emphasis role="lua">box.uuid()</emphasis> + </term> + <listitem> + <para> + Generates 128-bit (16 bytes) unique id. + </para> + <para> + Requires <emphasis>libuuid</emphasis> to be + installed. + </para> + </listitem> + </varlistentry> + <varlistentry> + <term> + <emphasis role="lua">box.uuid_hex()</emphasis> + </term> + <listitem> + <para> + Generates hex-string of 128-bit (16 bytes) unique id. + Returns 32-bytes string. + </para> + <bridgehead renderas="sect4">Example</bridgehead> + <programlisting> + lua box.uuid_hex() + --- + - a4f29fa0eb6d11e19f7737696d7fa8ff + ... + </programlisting> + </listitem> + </varlistentry> </variablelist> <variablelist> diff --git a/mod/box/CMakeLists.txt b/mod/box/CMakeLists.txt index 9b3ec9b45f..7c99f08466 100644 --- a/mod/box/CMakeLists.txt +++ b/mod/box/CMakeLists.txt @@ -39,4 +39,5 @@ set_source_files_properties(memcached.m PROPERTIES COMPILE_FLAGS "-Wno-uninitialized") tarantool_module("box" tuple.m index.m tree.m space.m port.m request.m - txn.m box.m box.lua.c box_lua.m memcached.m memcached-grammar.m) + txn.m box.m box.lua.c box_lua.m memcached.m memcached-grammar.m + box_lua_uuid.m) diff --git a/mod/box/box_lua.m b/mod/box/box_lua.m index 9b87474bc8..d0ea9fb50c 100644 --- a/mod/box/box_lua.m +++ b/mod/box/box_lua.m @@ -43,6 +43,8 @@ #include "space.h" #include "port.h" +#include "box_lua_uuid.h" + /* contents of box.lua */ extern const char box_lua[]; @@ -868,6 +870,8 @@ static int lbox_process(lua_State *L) static const struct luaL_reg boxlib[] = { {"process", lbox_process}, + {"uuid", lbox_uuid}, + {"uuid_hex", lbox_uuid_hex}, {NULL, NULL} }; diff --git a/mod/box/box_lua_uuid.h b/mod/box/box_lua_uuid.h new file mode 100644 index 0000000000..c2fbb0ba6b --- /dev/null +++ b/mod/box/box_lua_uuid.h @@ -0,0 +1,9 @@ +#ifndef __BOX_LUA_UUID_H__ +#define __BOX_LUA_UUID_H__ + +struct lua_State; + +int lbox_uuid(struct lua_State *L); +int lbox_uuid_hex(struct lua_State *L); + +#endif /* __BOX_LUA_UUID_H__ */ diff --git a/mod/box/box_lua_uuid.m b/mod/box/box_lua_uuid.m new file mode 100644 index 0000000000..dd4f6f0028 --- /dev/null +++ b/mod/box/box_lua_uuid.m @@ -0,0 +1,67 @@ +#include <dlfcn.h> +#include <string.h> +#include <stdio.h> +#include "box_lua_uuid.h" +#include "lua.h" +#include "lauxlib.h" +#include "lualib.h" + + +#define UUIDLIB_SOVERSION "1" +#define LIBNAME ( "libuuid.so." UUIDLIB_SOVERSION ) + +typedef unsigned char uuid_t[16]; + +static void (*uuid_generate)(uuid_t out); +static char *error; + +static void check_lib(struct lua_State *L) { + + if (uuid_generate) + return; + + if (error) + luaL_error( L, "box.uuid() error: %s", error ); + + void *dl = dlopen(LIBNAME, RTLD_LAZY); + if (!dl) { + error = strdup( dlerror() ); + luaL_error( L, "box.uuid() error: %s", error ); + } + + uuid_generate = dlsym(dl, "uuid_generate"); + if (!uuid_generate) { + error = strdup( dlerror() ); + luaL_error( L, "box.uuid() error: %s", error ); + } +} + + +int lbox_uuid(struct lua_State *L) { + check_lib(L); + + uuid_t uuid; + uuid_generate(uuid); + lua_pushlstring( L, (char *)uuid, sizeof(uuid_t) ); + + return 1; +} + +int lbox_uuid_hex(struct lua_State *L) { + + unsigned i; + char uuid_hex[ sizeof(uuid_t) * 2 + 1 ]; + + + check_lib(L); + + uuid_t uuid; + uuid_generate(uuid); + + for (i = 0; i < sizeof(uuid_t); i++) + snprintf( uuid_hex + i * 2, 3, "%02x", (unsigned)uuid[ i ] ); + + lua_pushlstring( L, uuid_hex, sizeof(uuid_t) * 2 ); + return 1; +} + diff --git a/test/box/lua.result b/test/box/lua.result index 60b5a3b842..f0d8ae6c44 100644 --- a/test/box/lua.result +++ b/test/box/lua.result @@ -1584,3 +1584,16 @@ lua box.dostring('return ...', 1, 2, 3) - 2 - 3 ... +# box.uuid() +lua box.dostring('return string.len(box.uuid())') +--- + - 16 +... +lua box.dostring('return string.len(box.uuid_hex())') +--- + - 32 +... +lua box.dostring('return string.match(box.uuid_hex(), "^[a-f0-9]+$")') ~= nil +--- + - true +... diff --git a/test/box/lua.test b/test/box/lua.test index 1efa745019..2b217be496 100644 --- a/test/box/lua.test +++ b/test/box/lua.test @@ -534,3 +534,9 @@ exec admin "lua box.dostring('abc=2')" exec admin "lua box.dostring('return abc')" exec admin "lua box.dostring('return ...', 1, 2, 3)" + +print """# box.uuid()""" +# exec admin "lua box.uuid()" +exec admin "lua box.dostring('return string.len(box.uuid())')" +exec admin "lua box.dostring('return string.len(box.uuid_hex())')" +exec admin """lua box.dostring('return string.match(box.uuid_hex(), "^[a-f0-9]+$")') ~= nil""" -- GitLab