简体   繁体   English

从Node.js中的回调获取列表

[英]Getting Lists from callback in nodejs

I am trying to get list of "servers" for a particular "stack" in Rackspace. 我正在尝试获取Rackspace中特定“堆栈”的“服务器”列表。 I have to do some processing of the Stack resource to get the server list as some of the servers are in a resource group(nested). 我必须对堆栈资源进行一些处理才能获取服务器列表,因为某些服务器位于资源组(嵌套)中。 I get each server through asynchronous call one by one. 我通过异步调用逐一获得每个服务器。 How to bundle them together and send at one go to the client? 如何将它们捆绑在一起并一次性发送给客户? Below is the code: 下面是代码:

   app.js

   function setClient(credentials)
   {
     var client = pkgcloud.orchestration.createClient({
       provider: 'rackspace',
       username: credentials.uname,
       apiKey: credentials.key,
       region: 'HKG'
     });
     return client;
   }

   app.io.route('ready', function(req) {
     var client = setClient(req.session.credentials);

     client.getStacks(function (err, stacks) {
        if (err) {
          req.io.emit("error", { error: err.result.error.message });
          return;
        }

        if (stacks.length > 0) {
          var stack = stacks[0].name;

          getSer(stack, client, req, 'init');
        }
        req.io.emit("showStacks", { stacks: stacks });
     });
   });

   app.io.route('create_stack', function(req) {
      var stack = req.data.stack_name;
      var tmpl = req.data.content;
      var client = setClient(req.session.credentials);

      client.createStack({
        name: stack,
        timeout: 60,
        template: tmpl // Heat template
       }, handle(req));
   });

   function handle(req) {
      return function handle(err, stack)
      {
         var client = setClient(req.session.credentials);

         if (err) {
            req.io.emit("error", { error: err.result.error.message });
            console.dir(err.result.error.message);
            return;
         }

         client.getStacks(function (err, stacks) {
            req.io.emit("showStacks", { stacks: stacks });
         });

         req.io.emit("status", {status: 'Stack created'});

         // Wait for status: CREATE_COMPLETE on our stack, and then callback
         stack.setWait({ status: 'CREATE_COMPLETE' }, 5000, function (err) {
            if (err) {
              req.io.emit("error", { error: err.result.error.message });
              console.dir(err);
              return;
            }

            client.getStacks(function (err, stacks) {
              req.io.emit("showStacks", { stacks: stacks });
            });

            client.getStack(stack, function (err, stack) {
               if (err) {
                  req.io.emit("error", { error: err.result.error.message             });
                  console.dir(err.result.error.message);
                  return;
                }
                req.io.emit("showStack", { stack: stack });
            });

            getSer(stack, client, req, 'create');
         });
      }
   }

   function getSer(stack, client, req, mode)
   {
      client.getResources(stack, function(err, resources) {
          if (err) {
             console.dir(err);
             req.io.emit("error", { error: err.result.error.message });
             return;
           }

           resources.forEach(function (resource) {
              var nestedlink = '';
              var nested = false;
              if (resource.links != undefined) {
                resource.links.forEach(function (link) {
                   if (link.rel == "nested") {
                      nestedlink = link.href;
                      nested = true;
                   }
                });
              }
              if (nested) {
                 var stack_name = nestedlink.substr(nestedlink.indexOf('stacks/')+7, nestedlink.lastIndexOf('/'));
                 getSer(stack_name, client, req, mode);
              } else {
                 var serId = resource.physicalResourceId;
                 var ser = serClient(req.session.credentials);
                 ser.getServer(serId, function (err, server) {
                   if (mode == 'init')
                     req.io.emit("showServer", { server: server});
                   else if (mode == 'create')
                     req.io.emit("stackCreate", { server: server});
                 });
              }
           });
      });
   }

Actually, the problem is pkgcloud has a method 'getResources' which given the stack name returns the resources. 实际上,问题在于pkgcloud有一个方法“ getResources”,该方法给出堆栈名称返回资源。 From which I get 'physical_resource_id' (server_id) of the server which is not in a group but for the servers which were created through 'OS::Heat::ResourceGroup' one's to do some extra work because the resource list has only a 'nested' link for it. 从中,我获得不在组中的服务器的“ physical_resource_id”(server_id),但是对于通过“ OS :: Heat :: ResourceGroup”创建的服务器,它会做一些额外的工作,因为资源列表中只有一个“嵌套”链接。 So I take the stack_name from the nested 'link' and get its server-id var stack_name = nestedlink.substr(nestedlink.indexOf('stacks/')+7, nestedlink.lastIndexOf('/')); 因此,我从嵌套的“链接”中获取var stack_name = nestedlink.substr(nestedlink.indexOf('stacks/')+7, nestedlink.lastIndexOf('/'));并获取其服务器var stack_name = nestedlink.substr(nestedlink.indexOf('stacks/')+7, nestedlink.lastIndexOf('/')); . Life would've been easy if pkgcloud had something like given a stack-name it'd return the servers list in it. 如果pkgcloud具有类似给定堆栈名称的内容,它将返回其中的服务器列表,生活将会很轻松。

The issue I mentioned in the comments ( https://github.com/pkgcloud/pkgcloud/issues/410 ) has been fixed now. 我在评论( https://github.com/pkgcloud/pkgcloud/issues/410 )中提到的问题现已修复。 With that fix you should be able to request a list of all resources for a stack, including nested resources . 使用该修复程序,您应该能够请求堆栈的所有资源的列表, 包括嵌套资源 Just do this in your code: 只需在您的代码中执行此操作:

  client.getResources(stack, { nestedDepth: XXX }, function(err, resources) {

where XXX is a sufficient nesting depth, depending on your stack. 其中XXX是足够的嵌套深度,具体取决于您的堆栈。

instead of: 代替:

  client.getResources(stack, function(err, resources) {

The fix to pkgcloud will be included in the next official release. pkgcloud的修复程序将包含在下一个正式版本中。 That might not become available for a couple of weeks or months so if you need to download this fix immediately, you can do so with the following command: 它可能在数周或数月内不可用,因此,如果您需要立即下载此修补程序,可以使用以下命令进行:

  npm install https://github.com/pkgcloud/pkgcloud/tarball/master

Alternatively, you could modify the pkgcloud dependency in your project's package.json like so: 另外,您可以在项目的package.json修改pkgcloud依赖关系,如下所示:

"pkgcloud": "git://github.com/pkgcloud/pkgcloud.git"

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM