Find file(s) in a directory on the node by pattern in Puppet

Viewed 26

How can I find a file in a directory on the node by using shell-patterns or regex?


What I want to do:

I download a tar file to /tmp/myfiles on the appropriate client and unpack this archive. From it come several deb files (about 10 of them). The filenames change with time, because there are version numbers integrated in the name.

The file names looks like:

  • package1_8.0-22.65.linux.x86_64.deb
  • package2_6.5-23.89.linux.x86_64.deb

I need to identify some of them (not all) to be able to install them via package with provider => dpkg.

The packages (like package1, package2) do not occur multiple times with different version numbers, so matching could be done easily without having to compare version numbers:

  • Shell pattern: package1_*.linux.x86_64.deb
  • Regex: ^package1_.+\.linux\.x86_64\.deb$

Is there a command or module in Puppet to find files by match pattern in a directory?

Or can I grab the result of exec with command => "ls /tmp/myfiles/..." and evaluate it?

1 Answers

Supposing that you mean that the tar file is downloaded as part of the catalog run, what you describe is not possible with Puppet and its standard Package resource type. Keep in mind the catalog-request cycle:

  1. The client gathers node facts.
  2. The client submits a catalog request bearing the gathered facts.
  3. The server uses the node's identity and facts, the manifests of the appropriate environment, and possibly the output of an external node classifier to build a catalog for the client.
  4. The client applies the catalog.

To create Package resources during step (3), Puppet needs to know at least the names of the packages. As you describe it, the names of the packages cannot be determined until step (4), which is too late.

You could have Puppet use the packages downloaded on a previous run by defining a custom fact that gathers their names from the filesystem, but that's risky and failure prone.

I think the whole endeavor is highly suspect and likely to cause you trouble. It would probably be better to put your packages in a local repository at your site and use either node data or a metapackage or both to control which are installed. But if you insist on downloading a tar full of DEBs, then unpacking and installing them, then your best bet is probably to use an Exec for the installation. Something like this:

# Ensure that the TAR file is in place
file { ${download_dir}:
  ensure => 'directory',
  # ...
}
file { "${download_dir}/packages.tar":
  ensure => 'file',
  # ...
}
-> exec { 'Install miscellaneous DEBs':
  path => ['/bin', '/usr/bin', '/sbin', /usr/sbin'],
  command => "rm '${download_dir}'/*.deb || :; tar xf '${download_dir}'/packages.tar && apt-get install '${download_dir}'/*.deb",
  provider => 'shell', 
}
Related