【问题标题】:Storing and retrieving Sockets in Redis在 Redis 中存储和检索套接字
【发布时间】:2012-06-01 15:09:26
【问题描述】:

我是 Node 和 Redis 的新手,如果我在这里遗漏了一些重要的东西,请原谅我。我正在尝试使用 node_redis 客户端将 Node.js net.Socket 对象存储在 Redis 中,因此我可以重用之前在此 Socket 上建立的连接。 我将套接字作为值存储为“用户”集的一部分:

client.sadd("users", username); //username is a string
client.hmset(username, "ip", socket.remoteAddress, "connection", net.Socket(socket));

在不同的点上,我将这个套接字检索为:

    client.smembers("users", function(err, replies) {

            replies.forEach(function(reply,i){
            if(recipient == reply) {       //recipient is the username i've got

                    client.hget(reply, "connection", function(err, obj) {
                    console.log("socket's remoteaddress = " +  net.Socket(obj).remoteAddress);
        net.Socket(obj).write("asdasdasd");
            });

            }
    });
    });

但是,: net.Socket(obj).remoteAddress);被记录为“未定义”。 还, net.Socket(obj).write("asdasdasd");给我和错误说:

错误:此套接字已关闭。

所以我想我的问题是 - 你可以在 Redis 中以这种方式存储 Socket 并期望它们在检索时工作吗?有没有正确/更好的方法来做到这一点?

附:我尝试在不强制转换为 net.Socket 的情况下检索 Socket,但它仍然没有任何好处。

【问题讨论】:

    标签: node.js redis


    【解决方案1】:

    套接字和套接字 API(例如 Berkeley Sockets)本质上处理特定于系统的特殊资源,在远程系统上存储或引用这些资源没有任何意义,甚至为此进行序列化。

    尽管实际上,套接字通常由file descriptors 唯一标识,因此您可以轻松地将那个小的唯一整数存储在数据库中以供以后访问;但是,该整数仅在该进程实例中该套接字的活动生命周期内才有意义。像这样的策略将充满挑战,主要与套接字文件描述符编号的瞬态特性有关。

    【讨论】:

    • 它看起来确实是在黑暗中拍摄的。我也可以使用 IP 地址,但我的客户端隐藏在 NAT 后面,而且我还有其他一些问题让我无法打开与我存储的 IP 地址的新连接。
    【解决方案2】:

    正如@maerics 所说,redis 只存储字符串。所以你的套接字数据将被破坏并给出未定义的答案。

    你可以像这样存储你的套接字。

    var OBJECT = Object.prototype;
    OBJECT.rhash = {};
    OBJECT.rset = function(id, object) {
      OBJECT.rhash[id] = object;
      return id;
    };
    OBJECT.rget = function(id) {
      return OBJECT.rhash[id];
    };
    

    这将存储对该对象的引用并再次重用它..

    var id = OBJECT.rset("a123",socket);
    var ref = OBJECT.rget("a123");
    console.log(ref.remoteAddress);
    

    【讨论】:

      【解决方案3】:

      关于 IP 地址,它位于不同的哈希键上(不是connection,而是ip)。因此,要获取您刚刚从该键中读取的值:

      client.hget(reply, "ip", function(err, obj) {
         console.log("socket's remoteaddress = " +  obj);
      });
      

      【讨论】:

      • 是的,我可以很好地阅读它,并且正在将它用于其他用途。但我希望直接使用连接本身。
      猜你喜欢
      • 2015-11-23
      • 1970-01-01
      • 1970-01-01
      • 2017-07-04
      • 1970-01-01
      • 2020-03-25
      • 1970-01-01
      • 2013-02-25
      • 1970-01-01
      相关资源
      最近更新 更多