Comment passer des données entre plusieurs états Lua (multi-thread)?

J’initie le pool de connexions Redis dans redis.lua , en appelant de C, j’ai un redis_lua_state , cet état de Lua est lancé une fois et les autres threads n’en obtiennent qu’un.

Alors qu’il y a une requête HTTP (thread de travail), je dois récupérer une connexion redis à partir de redis_lua_state , puis créer un autre état Lua pour charger un autre script Lua. Ces scripts utiliseront cette connexion redis pour communiquer avec Redis. Comment faire? Ou comment concevoir mes scripts Lua pour simplifier les choses?


Exemple de code:

  /* on main thread, to init redis pool connection */ lua_State *g_ls = NULL; lua_State *init_redis_pool(void) { int ret = 0; g_ls = luaL_newstate(); lua_State *ls = g_ls; luaL_openlibs(ls); ret = luaL_loadfile(ls, "redis.lua"); const char *err; (void)err; /* preload */ ret = lua_pcall(ls, 0, 0, 0); lua_getglobal(ls, "init_redis_pool"); ret = lua_pcall(ls, 0, 0, 0); return ls; } /* worker thread */ int worker() { ... lua_State *ls = luaL_newstate(); ret = luaL_loadfile(ls, "run.lua"); /* How to fetch data from g_ls? */ ... lua_getglobal(ls, "run") ret = lua_pcall(ls, 0, 0, 0) lua_close(ls); ... return 0; } 

Si vos états Lua sont séparés, il n’y a aucun moyen de le faire. Votre thread de travail devra initialiser la connexion Redis et en effectuer le traitement.

Une façon de le faire est d’implémenter des variables de copie entre les états de Lua du côté C. J’ai fait la même chose dans mon projet ERP, mais cela demande un peu de tracas, notamment en ce qui concerne la copie de données utilisateur.

Ce que j’ai fait est d’implémenter une sorte de système de variable super globale (une classe C dans mon instance) implémenté sous la forme __index et __newindex de la table globale, qui est un proxy de la table globale Lua par défaut. Lorsque vous définissez une variable globale, __newindex copie dans ce super global. Lorsqu’un autre État de Lua tenterait d’accéder à ce global, il le récupérerait à partir de la même structure.

Et alors, la connexion redis pourrait être un mutex verrouillé partagé. Ainsi, lorsqu’un État y accède, l’autre ne le peut pas, par exemple.

Bien sûr, il faut également prendre en charge l’access aux globaux par défaut de Lua.

Alternativement, vous pouvez vérifier les voies de Lua , si c’est une option (je n’ai aucune expérience des Redis, alors je ne sais pas à quel point Lua est ouverte, mais je vois que vous avez un access complet à l’API C, donc cela devrait fonctionner).