Puppet代理挂起并最终导致内存分配错误

时间:2014-06-04 09:25:59

标签: performance vagrant puppet

我正在使用傀儡作为Vagrant的供应者,并且我遇到了一个问题,即当我做“流浪汉条款”时Puppet将会持续很长时间。使用“vagrant up”从头开始构建盒子似乎不是问题,只是后续的规定。

如果我打开木偶调试并观察它挂起的位置,它似乎停在各种看似随意的点上,第一点是:

Info: Applying configuration version '1401868442'
Debug: Prefetching yum resources for package
Debug: Executing '/bin/rpm --version'
Debug: Executing '/bin/rpm -qa --nosignature --nodigest --qf '%{NAME} %|EPOCH?{%    {EPOCH}}:{0}| %{VERSION} %{RELEASE} %{ARCH}\n''

我自己立即在服务器上执行此命令。

最终,它越过了这个并继续。使用摘要选项,在等待很长时间完成后,我得到以下内容:

Debug: Finishing transaction 70191217833880
Debug: Storing state
Debug: Stored state in 9.39 seconds
Notice: Finished catalog run in 1493.99 seconds
Changes:
        Total: 2
Events:
      Failure: 2
      Success: 2
        Total: 4
Resources:
        Total: 18375
      Changed: 2
       Failed: 2
      Skipped: 35
  Out of sync: 4
Time:
         User: 0.00
       Anchor: 0.01
     Schedule: 0.01
      Yumrepo: 0.07
       Augeas: 0.12
      Package: 0.18
         Exec: 0.96
      Service: 1.07
        Total: 108.93
     Last run: 1401869964
   Config retrieval: 16.49
   Mongodb database: 3.99
         File: 76.60
   Mongodb user: 9.43
Version:
       Config: 1401868442
       Puppet: 3.4.3

这对我来说似乎没有什么帮助,因为总时间为108秒,那么其他1385秒又消失了?

在整个过程中,Puppet似乎正在敲打这个盒子,耗费了大量的CPU,但似乎还没有推进。它使用的内存似乎在不断增加。当我启动命令时,top看起来像这样:

Cpu(s): 10.2%us,  2.2%sy,  0.0%ni, 85.5%id,  2.2%wa,  0.0%hi,  0.0%si,  0.0%st
Mem:   4956928k total,  2849296k used,  2107632k free,    63464k buffers
Swap:   950264k total,    26688k used,   923576k free,   445692k cached

  PID USER      PR  NI  VIRT  RES  SHR S %CPU %MEM    TIME+  COMMAND
28486 root      20   0  439m 334m 3808 R 97.5  6.9   2:02.92 puppet
   22 root      20   0     0    0    0 S  1.3  0.0   0:07.55 kblockd/0
18276 mongod    20   0  788m  31m 3040 S  1.3  0.6   2:31.82 mongod
20756 jboss-as  20   0 3081m 1.5g  21m S  1.3 31.4   7:13.15 java
20930 elastics  20   0 2340m 236m 6580 S  1.0  4.9   1:44.80 java
  266 root      20   0     0    0    0 S  0.3  0.0   0:03.85 jbd2/dm-0-8
22717 vagrant   20   0 98.0m 2252 1276 S  0.3  0.0   0:01.81 sshd
28762 vagrant   20   0 15036 1228  932 R  0.3  0.0   0:00.10 top
    1 root      20   0 19364 1180  964 S  0.0  0.0   0:00.86 init

对我来说,这似乎很好,有超过2GB的可用内存和大量可用的交换。我的最大打开文件限制为1024。

大约10-15分钟后,控制台输出仍然没有进展,但top看起来像这样:

Cpu(s): 11.2%us,  1.6%sy,  0.0%ni, 86.9%id,  0.0%wa,  0.0%hi,  0.3%si,  0.0%s
Mem:   4956928k total,  3834376k used,  1122552k free,    64248k buffers
Swap:   950264k total,    24408k used,   925856k free,   445728k cached

  PID USER      PR  NI  VIRT  RES  SHR S %CPU %MEM    TIME+  COMMAND
28486 root      20   0 1397m 1.3g 3808 R 99.6 26.7  15:16.19 puppet
18276 mongod    20   0  788m  31m 3040 R  1.7  0.6   2:45.03 mongod
20756 jboss-as  20   0 3081m 1.5g  21m S  1.3 31.4   7:25.93 java
20930 elastics  20   0 2340m 238m 6580 S  0.7  4.9   1:52.03 java
 8486 root      20   0  308m  952  764 S  0.3  0.0   0:06.03 VBoxService

正如你所看到的,木偶现在正在使用更多的记忆,它似乎以这种方式继续存在。它正在构建的盒子有5GB的RAM,所以我不希望它有内存问题。然而,经过漫长的等待,我得到“无法分配内存 - 分叉(2)”

运行无限制-a,我得到:

core file size          (blocks, -c) 0
data seg size           (kbytes, -d) unlimited
scheduling priority             (-e) 0
file size               (blocks, -f) unlimited
pending signals                 (-i) 38566
max locked memory       (kbytes, -l) 64
max memory size         (kbytes, -m) unlimited
open files                      (-n) 1024
pipe size            (512 bytes, -p) 8
POSIX message queues     (bytes, -q) 819200
real-time priority              (-r) 0
stack size              (kbytes, -s) 10240
cpu time               (seconds, -t) unlimited
max user processes              (-u) 1024
virtual memory          (kbytes, -v) unlimited
file locks                      (-x) unlimited

对我来说再次看起来很好......

说实话,我完全不知道如何解决这个问题,或者是什么导致问题。

非常感谢任何帮助或见解!

修改

所以我最终设法解决了这个问题......它归结为使用recurse和一个大目录的文件指令。有问题的目标目录包含大约2GB的文件,而puppet花费了大量的时间将其加载到内存中并进行哈希和比较。我第一次站起服务器,目录相对空,所以检查很快,但随后放入了其他资源,大大增加了它的大小,这意味着后续运行需要更长的时间。

最终抛出的内存错误是因为,我只能假设,Puppet正在将整个内容加载到内存中以便完成它的工作......

我找到了一种使用递归功能的方法,现在我试图像瘟疫一样避免它......

1 个答案:

答案 0 :(得分:0)

是的,文件类型上recurse参数的问题在于它检查每个文件的校验和,这在大型目录上实际加快了。

正如Felix建议的那样,使用checksum => none是解决问题的一种方法,另一种方法是使用exec来完成您尝试执行的任务(例如chmod或chown整个目录)本机任务,除非检查它是否已经完成。

类似的东西:

define check_mode($mode) {
  exec { "/bin/chmod $mode $name":
    unless => "/bin/sh -c '[ $(/usr/bin/stat -c %a $name) == $mode ]'",
  }
}

取自http://projects.puppetlabs.com/projects/1/wiki/File_Permission_Check_Patterns