新手问题 求教多重 hash 如何取值

danielfeng · 2015年04月11日 · 最后由 danielfeng 回复于 2015年04月14日 · 3704 次阅读

求教如何在如下数据中取 PublicPort 或 Image

[#<Docker::Container:0x00000005195578 @id="8aba2f87cdf5e5d340f30fef8e5df8f58d990eab1c70583d4fef3a8fa83de3f2", @info={"Command"=>"/bin/bash", "Created"=>1427722904, "Image"=>"ddddd:latest", "Names"=>["/clever_pike"], "Ports"=>[{"IP"=>"0.0.0.0", "PrivatePort"=>80, "PublicPort"=>10280, "Type"=>"tcp"}], "Status"=>"Up 10 days", "id"=>"8aba2f87cdf5e5d340f30fef8e5df8f58d990eab1c70583d4fef3a8fa83de3f2"}, @connection=#<Docker::Connection:0x00000004aaadf8 @url="unix:///", @options={:socket=>"/var/run/docker.sock"}>>, #<Docker::Container:0x00000005195488 @id="c95642d254f1b716debbc8f5381b1234aff69c92db87a43e9b6f64216d1471b3", @info={"Command"=>"/bin/bash", "Created"=>1427722902, "Image"=>"bbbbbbb:latest", "Names"=>["/serene_heisenberg"], "Ports"=>[{"IP"=>"0.0.0.0", "PrivatePort"=>80, "PublicPort"=>10180, "Type"=>"tcp"}], "Status"=>"Up 10 days", "id"=>"c95642d254f1b716debbc8f5381b1234aff69c92db87a43e9b6f64216d1471b3"}, @connection=#<Docker::Connection:0x00000004aaadf8 @url="unix:///", @options={:socket=>"/var/run/docker.sock"}>>]

以上直接调用 docker-api,d=Docker::Container.all 获得,相应源代码如下。

def self.all(opts = {}, conn = Docker.connection)
    hashes = Docker::Util.parse_json(conn.get('/containers/json', opts)) || []
    hashes.map { |hash| new(conn, hash) }
end

通过 pp 结果输出如下

[#<Docker::Container:0x007fe34c722018
 @connection=
  #<Docker::Connection:0x007fe34d353af8
   @options={:socket=>"/var/run/docker.sock"},
   @url="unix:///">,
 @id="c95642d254f1b716debbc8f5381b1234aff69c92db87a43e9b6f64216d1471b3",
 @info=
  {"Command"=>"/bin/bash",
   "Created"=>1427722902,
   "Image"=>"dddd:latest",
   "Names"=>["/serene_heisenberg"],
   "Ports"=>
    [{"IP"=>"0.0.0.0",
      "PrivatePort"=>80,
      "PublicPort"=>10180,
      "Type"=>"tcp"}],
   "Status"=>"Up 12 days",
   "id"=>"c95642d254f1b716debbc8f5381b1234aff69c92db87a43e9b6f64216d1471b3"}>,
#<Docker::Container:0x007fe34c721f28
 @connection=
  #<Docker::Connection:0x007fe34d353af8
   @options={:socket=>"/var/run/docker.sock"},
   @url="unix:///">,
 @id="5583df725fa5917eee6609210fee422d6d1d0059f8a9c630bdbf407d6cd014fc",
 @info=
  {"Command"=>"/bin/bash",
   "Created"=>1427722900,
   "Image"=>"vvvvv:latest",
   "Names"=>["/adoring_franklin"],
   "Ports"=>
    [{"IP"=>"0.0.0.0",
      "PrivatePort"=>80,
      "PublicPort"=>10080,
      "Type"=>"tcp"}],
   "Status"=>"Up 12 days",
   "id"=>"5583df725fa5917eee6609210fee422d6d1d0059f8a9c630bdbf407d6cd014fc"}>]
name = params.fetch(:user)[:name]

第十条

#1 楼 @ericguo 貌似这样获取不了dn2.fetch('@info')["Image"]是不是我写错了?

irb(main):082:0> dn2.fetch('@info')["Image"]
TypeError: no implicit conversion of String into Integer

直接可以加 [0] 可以获取一行数据

irb(main):084:0* dn2[0]
=> #<Docker::Container:0x000000016dcdf0 @id="910ff683565edada2e4508b7cbde61be74d16d0fe3afff6e2254a7e187f82d6d", @info={"Command"=>"/bin/bash", "Created"=>1428564466, "Image"=>"dn:latest", "Names"=>["/goofy_bardeen"], "Ports"=>[{"IP"=>"0.0.0.0", "PrivatePort"=>3000, "PublicPort"=>81, "Type"=>"tcp"}, {"PrivatePort"=>80, "Type"=>"tcp"}, {"PrivatePort"=>443, "Type"=>"tcp"}], "Status"=>"Up 2 days", "id"=>"910ff683565edada2e4508b7cbde61be74d16d0fe3afff6e2254a7e187f82d6d"}, @connection=#<Docker::Connection:0x007fe34d353af8 @url="unix:///", @options={:socket=>"/var/run/docker.sock"}>>

#2 楼 @danielfeng 那就说明 dn2 是一个数组对象,可以加个断点,然后查看一下 dn2,parse_json 后是一个对象,不是 hashes

#3 楼 @ericguo 是不是将所有@info提取出来?这个有啥参数?断点是?

#4 楼 @danielfeng 断点就是在这里停下来看一下,我觉得这样的话,写成:

dn2[0].info[:Image]

应该可以拿到第一个 Image 的值。

#5 楼 @ericguo dn2[0].info[:Image]成功了,但是我要拿到 image 的 list 应该怎么写?

#5 楼 @ericguo 因为以前只写 shell,在 ruby 也用 for 之类的来存入变量 list?还是有更简单的方法?前面想到。。让 [0] 中的 0 变成一个 i++ 来个循环。。

dn2.collect {|d| d.info[:Image]}

#8 楼 @ericguo 厉害我前面写了 for。。。shell 后遗症,但我想吧后面的:Name 也一同输出?变成一个 2 维数组。 ddd,centos aaa,redhat

names = Array.new
for i in 0...dn.length
 tmp = dn[i].info["Image"]
 names.push(tmp)
end
dn2.collect { |d| [d.info[:Image], d.info[:Name]] }

#10 楼 @ericguo 超级感谢,在追问一个问题。我获得到了 image 的一个 list,["aaa","bbb"] 想在 rails 的 erb 里面动态生成 html 应该如何

<td><a class="ng-binding" href="http://192.168.209.9:10080" target="view_window"><%= @image[0]%></a></td>
<td><a class="label label-primary" href="http://192.168.209.9:10080/" target="view_window">web</a></td>

<td><a class="ng-binding" href="http://192.168.209.9:10080" target="view_window"><%= @image[1]%></a></td>
<td><a class="label label-primary" href="http://192.168.209.9:10080/" target="view_window">web</a></td>

#10 楼 @ericguo 关于 html 已经成功,另外想问下。提取包含某字符的组织行应该如何?提取如下 ab 的数组。

[["abc:latest", 11080], ["abc2:latest", 10980], ["bbb:latest", 10880]]

#12 楼 @danielfeng

s.find_all {|v| v[0].start_with? 'ab'}

#13 楼 @ericguo 感谢!我试试

需要 登录 后方可回复, 如果你还没有账号请点击这里 注册