summaryrefslogtreecommitdiff
path: root/examples/redis-unstable/tests/modules/usercall.c
diff options
context:
space:
mode:
Diffstat (limited to 'examples/redis-unstable/tests/modules/usercall.c')
-rw-r--r--examples/redis-unstable/tests/modules/usercall.c230
1 files changed, 0 insertions, 230 deletions
diff --git a/examples/redis-unstable/tests/modules/usercall.c b/examples/redis-unstable/tests/modules/usercall.c
deleted file mode 100644
index cc28817..0000000
--- a/examples/redis-unstable/tests/modules/usercall.c
+++ /dev/null
@@ -1,230 +0,0 @@
-#include "redismodule.h"
-#include <pthread.h>
-#include <assert.h>
-
-#define UNUSED(V) ((void) V)
-
-RedisModuleUser *user = NULL;
-
-int call_without_user(RedisModuleCtx *ctx, RedisModuleString **argv, int argc) {
- if (argc < 2) {
- return RedisModule_WrongArity(ctx);
- }
-
- const char *cmd = RedisModule_StringPtrLen(argv[1], NULL);
-
- RedisModuleCallReply *rep = RedisModule_Call(ctx, cmd, "Ev", argv + 2, (size_t)argc - 2);
- if (!rep) {
- RedisModule_ReplyWithError(ctx, "NULL reply returned");
- } else {
- RedisModule_ReplyWithCallReply(ctx, rep);
- RedisModule_FreeCallReply(rep);
- }
- return REDISMODULE_OK;
-}
-
-int call_with_user_flag(RedisModuleCtx *ctx, RedisModuleString **argv, int argc) {
- if (argc < 3) {
- return RedisModule_WrongArity(ctx);
- }
-
- RedisModule_SetContextUser(ctx, user);
-
- /* Append Ev to the provided flags. */
- RedisModuleString *flags = RedisModule_CreateStringFromString(ctx, argv[1]);
- RedisModule_StringAppendBuffer(ctx, flags, "Ev", 2);
-
- const char* flg = RedisModule_StringPtrLen(flags, NULL);
- const char* cmd = RedisModule_StringPtrLen(argv[2], NULL);
-
- RedisModuleCallReply* rep = RedisModule_Call(ctx, cmd, flg, argv + 3, (size_t)argc - 3);
- if (!rep) {
- RedisModule_ReplyWithError(ctx, "NULL reply returned");
- } else {
- RedisModule_ReplyWithCallReply(ctx, rep);
- RedisModule_FreeCallReply(rep);
- }
- RedisModule_FreeString(ctx, flags);
-
- return REDISMODULE_OK;
-}
-
-int add_to_acl(RedisModuleCtx *ctx, RedisModuleString **argv, int argc) {
- if (argc != 2) {
- return RedisModule_WrongArity(ctx);
- }
-
- size_t acl_len;
- const char *acl = RedisModule_StringPtrLen(argv[1], &acl_len);
-
- RedisModuleString *error;
- int ret = RedisModule_SetModuleUserACLString(ctx, user, acl, &error);
- if (ret) {
- size_t len;
- const char * e = RedisModule_StringPtrLen(error, &len);
- RedisModule_ReplyWithError(ctx, e);
- return REDISMODULE_OK;
- }
-
- RedisModule_ReplyWithSimpleString(ctx, "OK");
-
- return REDISMODULE_OK;
-}
-
-int get_acl(RedisModuleCtx *ctx, RedisModuleString **argv, int argc) {
- REDISMODULE_NOT_USED(argv);
-
- if (argc != 1) {
- return RedisModule_WrongArity(ctx);
- }
-
- RedisModule_Assert(user != NULL);
-
- RedisModuleString *acl = RedisModule_GetModuleUserACLString(user);
-
- RedisModule_ReplyWithString(ctx, acl);
-
- RedisModule_FreeString(NULL, acl);
-
- return REDISMODULE_OK;
-}
-
-int reset_user(RedisModuleCtx *ctx, RedisModuleString **argv, int argc) {
- REDISMODULE_NOT_USED(argv);
-
- if (argc != 1) {
- return RedisModule_WrongArity(ctx);
- }
-
- if (user != NULL) {
- RedisModule_FreeModuleUser(user);
- }
-
- user = RedisModule_CreateModuleUser("module_user");
-
- RedisModule_ReplyWithSimpleString(ctx, "OK");
-
- return REDISMODULE_OK;
-}
-
-typedef struct {
- RedisModuleString **argv;
- int argc;
- RedisModuleBlockedClient *bc;
-} bg_call_data;
-
-void *bg_call_worker(void *arg) {
- bg_call_data *bg = arg;
- RedisModuleBlockedClient *bc = bg->bc;
-
- // Get Redis module context
- RedisModuleCtx *ctx = RedisModule_GetThreadSafeContext(bg->bc);
-
- // Acquire GIL
- RedisModule_ThreadSafeContextLock(ctx);
-
- // Set user
- RedisModule_SetContextUser(ctx, user);
-
- // Call the command
- size_t format_len;
- RedisModuleString *format_redis_str = RedisModule_CreateString(NULL, "v", 1);
- const char *format = RedisModule_StringPtrLen(bg->argv[1], &format_len);
- RedisModule_StringAppendBuffer(NULL, format_redis_str, format, format_len);
- RedisModule_StringAppendBuffer(NULL, format_redis_str, "E", 1);
- format = RedisModule_StringPtrLen(format_redis_str, NULL);
- const char *cmd = RedisModule_StringPtrLen(bg->argv[2], NULL);
- RedisModuleCallReply *rep = RedisModule_Call(ctx, cmd, format, bg->argv + 3, (size_t)bg->argc - 3);
- RedisModule_FreeString(NULL, format_redis_str);
-
- /* Free the arguments within GIL to prevent simultaneous freeing in main thread. */
- for (int i=0; i<bg->argc; i++)
- RedisModule_FreeString(ctx, bg->argv[i]);
- RedisModule_Free(bg->argv);
- RedisModule_Free(bg);
-
- // Release GIL
- RedisModule_ThreadSafeContextUnlock(ctx);
-
- // Reply to client
- if (!rep) {
- RedisModule_ReplyWithError(ctx, "NULL reply returned");
- } else {
- RedisModule_ReplyWithCallReply(ctx, rep);
- RedisModule_FreeCallReply(rep);
- }
-
- // Unblock client
- RedisModule_UnblockClient(bc, NULL);
-
- // Free the Redis module context
- RedisModule_FreeThreadSafeContext(ctx);
-
- return NULL;
-}
-
-int call_with_user_bg(RedisModuleCtx *ctx, RedisModuleString **argv, int argc)
-{
- UNUSED(argv);
- UNUSED(argc);
-
- /* Make sure we're not trying to block a client when we shouldn't */
- int flags = RedisModule_GetContextFlags(ctx);
- int allFlags = RedisModule_GetContextFlagsAll();
- if ((allFlags & REDISMODULE_CTX_FLAGS_MULTI) &&
- (flags & REDISMODULE_CTX_FLAGS_MULTI)) {
- RedisModule_ReplyWithSimpleString(ctx, "Blocked client is not supported inside multi");
- return REDISMODULE_OK;
- }
- if ((allFlags & REDISMODULE_CTX_FLAGS_DENY_BLOCKING) &&
- (flags & REDISMODULE_CTX_FLAGS_DENY_BLOCKING)) {
- RedisModule_ReplyWithSimpleString(ctx, "Blocked client is not allowed");
- return REDISMODULE_OK;
- }
-
- /* Make a copy of the arguments and pass them to the thread. */
- bg_call_data *bg = RedisModule_Alloc(sizeof(bg_call_data));
- bg->argv = RedisModule_Alloc(sizeof(RedisModuleString*)*argc);
- bg->argc = argc;
- for (int i=0; i<argc; i++)
- bg->argv[i] = RedisModule_HoldString(ctx, argv[i]);
-
- /* Block the client */
- bg->bc = RedisModule_BlockClient(ctx, NULL, NULL, NULL, 0);
-
- /* Start a thread to handle the request */
- pthread_t tid;
- int res = pthread_create(&tid, NULL, bg_call_worker, bg);
- assert(res == 0);
- pthread_detach(tid);
-
- return REDISMODULE_OK;
-}
-
-int RedisModule_OnLoad(RedisModuleCtx *ctx, RedisModuleString **argv, int argc) {
- REDISMODULE_NOT_USED(argv);
- REDISMODULE_NOT_USED(argc);
-
- if (RedisModule_Init(ctx,"usercall",1,REDISMODULE_APIVER_1)== REDISMODULE_ERR)
- return REDISMODULE_ERR;
-
- if (RedisModule_CreateCommand(ctx,"usercall.call_without_user", call_without_user,"write",0,0,0) == REDISMODULE_ERR)
- return REDISMODULE_ERR;
-
- if (RedisModule_CreateCommand(ctx,"usercall.call_with_user_flag", call_with_user_flag,"write",0,0,0) == REDISMODULE_ERR)
- return REDISMODULE_ERR;
-
- if (RedisModule_CreateCommand(ctx, "usercall.call_with_user_bg", call_with_user_bg, "write", 0, 0, 0) == REDISMODULE_ERR)
- return REDISMODULE_ERR;
-
- if (RedisModule_CreateCommand(ctx, "usercall.add_to_acl", add_to_acl, "write",0,0,0) == REDISMODULE_ERR)
- return REDISMODULE_ERR;
-
- if (RedisModule_CreateCommand(ctx,"usercall.reset_user", reset_user,"write",0,0,0) == REDISMODULE_ERR)
- return REDISMODULE_ERR;
-
- if (RedisModule_CreateCommand(ctx,"usercall.get_acl", get_acl,"write",0,0,0) == REDISMODULE_ERR)
- return REDISMODULE_ERR;
-
- return REDISMODULE_OK;
-}