diff --git a/lib/puppet/face/module/install.rb b/lib/puppet/face/module/install.rb index db0a0eb91..b098c8866 100644 --- a/lib/puppet/face/module/install.rb +++ b/lib/puppet/face/module/install.rb @@ -1,173 +1,172 @@ # encoding: UTF-8 Puppet::Face.define(:module, '1.0.0') do action(:install) do - summary "Install a module from a repository or release archive." + summary "Install a module from the Puppet Forge or a release archive." description <<-EOT - Installs a module from the Puppet Forge, from a release archive file - on-disk, or from a private Forge-like repository. + Installs a module from the Puppet Forge or from a release archive file. The specified module will be installed into the directory specified with the `--target-dir` option, which defaults to #{Puppet.settings[:modulepath].split(File::PATH_SEPARATOR).first}. EOT returns "Pathname object representing the path to the installed module." examples <<-EOT Install a module: $ puppet module install puppetlabs-vcsrepo Preparing to install into /etc/puppet/modules ... Downloading from http://forge.puppetlabs.com ... Installing -- do not interrupt ... /etc/puppet/modules └── puppetlabs-vcsrepo (v0.0.4) Install a module to a specific environment: $ puppet module install puppetlabs-vcsrepo --environment development Preparing to install into /etc/puppet/environments/development/modules ... Downloading from http://forge.puppetlabs.com ... Installing -- do not interrupt ... /etc/puppet/environments/development/modules └── puppetlabs-vcsrepo (v0.0.4) Install a specific module version: $ puppet module install puppetlabs-vcsrepo -v 0.0.4 Preparing to install into /etc/puppet/modules ... Downloading from http://forge.puppetlabs.com ... Installing -- do not interrupt ... /etc/puppet/modules └── puppetlabs-vcsrepo (v0.0.4) Install a module into a specific directory: $ puppet module install puppetlabs-vcsrepo --target-dir=/usr/share/puppet/modules Preparing to install into /usr/share/puppet/modules ... Downloading from http://forge.puppetlabs.com ... Installing -- do not interrupt ... /usr/share/puppet/modules └── puppetlabs-vcsrepo (v0.0.4) Install a module into a specific directory and check for dependencies in other directories: $ puppet module install puppetlabs-vcsrepo --target-dir=/usr/share/puppet/modules --modulepath /etc/puppet/modules Preparing to install into /usr/share/puppet/modules ... Downloading from http://forge.puppetlabs.com ... Installing -- do not interrupt ... /usr/share/puppet/modules └── puppetlabs-vcsrepo (v0.0.4) Install a module from a release archive: $ puppet module install puppetlabs-vcsrepo-0.0.4.tar.gz Preparing to install into /etc/puppet/modules ... Downloading from http://forge.puppetlabs.com ... Installing -- do not interrupt ... /etc/puppet/modules └── puppetlabs-vcsrepo (v0.0.4) Install a module from a release archive and ignore dependencies: $ puppet module install puppetlabs-vcsrepo-0.0.4.tar.gz --ignore-dependencies Preparing to install into /etc/puppet/modules ... Installing -- do not interrupt ... /etc/puppet/modules └── puppetlabs-vcsrepo (v0.0.4) EOT arguments "" option "--force", "-f" do summary "Force overwrite of existing module, if any." description <<-EOT Force overwrite of existing module, if any. EOT end option "--target-dir DIR", "-i DIR" do summary "The directory into which modules are installed." description <<-EOT The directory into which modules are installed; defaults to the first directory in the modulepath. Specifying this option will change the installation directory, and will use the existing modulepath when checking for dependencies. If you wish to check a different set of directories for dependencies, you must also use the `--environment` or `--modulepath` options. EOT end option "--ignore-dependencies" do summary "Do not attempt to install dependencies" description <<-EOT Do not attempt to install dependencies. EOT end option "--modulepath MODULEPATH" do default_to { Puppet.settings[:modulepath] } summary "Which directories to look for modules in" description <<-EOT The list of directories to check for modules. When installing a new module, this setting determines where the module tool will look for its dependencies. If the `--target dir` option is not specified, the first directory in the modulepath will also be used as the install directory. When installing a module into an environment whose modulepath is specified in puppet.conf, you can use the `--environment` option instead, and its modulepath will be used automatically. This setting should be a list of directories separated by the path separator character. (The path separator is `:` on Unix-like platforms and `;` on Windows.) EOT end option "--version VER", "-v VER" do summary "Module version to install." description <<-EOT Module version to install; can be an exact version or a requirement string, eg '>= 1.0.3'. Defaults to latest version. EOT end option "--environment NAME" do default_to { "production" } summary "The target environment to install modules into." description <<-EOT The target environment to install modules into. Only applicable if multiple environments (with different modulepaths) have been configured in puppet.conf. EOT end when_invoked do |name, options| sep = File::PATH_SEPARATOR if options[:target_dir] options[:modulepath] = "#{options[:target_dir]}#{sep}#{options[:modulepath]}" end Puppet.settings[:modulepath] = options[:modulepath] options[:target_dir] = Puppet.settings[:modulepath].split(sep).first Puppet.notice "Preparing to install into #{options[:target_dir]} ..." Puppet::ModuleTool::Applications::Installer.run(name, options) end when_rendering :console do |return_value, name, options| if return_value[:result] == :failure Puppet.err(return_value[:error][:multiline]) exit 1 else tree = Puppet::ModuleTool.build_tree(return_value[:installed_modules], return_value[:install_dir]) return_value[:install_dir] + "\n" + Puppet::ModuleTool.format_tree(tree) end end end end diff --git a/lib/puppet/face/module/search.rb b/lib/puppet/face/module/search.rb index 7632f56de..4f27b65e5 100644 --- a/lib/puppet/face/module/search.rb +++ b/lib/puppet/face/module/search.rb @@ -1,88 +1,88 @@ require 'puppet/util/terminal' Puppet::Face.define(:module, '1.0.0') do action(:search) do - summary "Search a repository for a module." + summary "Search the Puppet Forge for a module." description <<-EOT - Searches a repository for modules whose names, descriptions, or keywords + Searches the Puppet Forge for modules whose names, descriptions, or keywords match the provided search term. EOT returns "Array of module metadata hashes" examples <<-EOT - Search the default repository for a module: + Search the Puppet Forge for a module: $ puppet module search puppetlabs NAME DESCRIPTION AUTHOR KEYWORDS bacula This is a generic Apache module @puppetlabs backups EOT arguments "" when_invoked do |term, options| Puppet::ModuleTool::Applications::Searcher.run(term, options) end when_rendering :console do |results, term, options| return "No results found for '#{term}'." if results.empty? padding = ' ' headers = { 'full_name' => 'NAME', 'desc' => 'DESCRIPTION', 'author' => 'AUTHOR', 'tag_list' => 'KEYWORDS', } min_widths = Hash[ *headers.map { |k,v| [k, v.length] }.flatten ] min_widths['full_name'] = min_widths['author'] = 12 min_width = min_widths.inject(0) { |sum,pair| sum += pair.last } + (padding.length * (headers.length - 1)) terminal_width = [Puppet::Util::Terminal.width, min_width].max columns = results.inject(min_widths) do |hash, result| { 'full_name' => [ hash['full_name'], result['full_name'].length ].max, 'desc' => [ hash['desc'], result['desc'].length ].max, 'author' => [ hash['author'], "@#{result['author']}".length ].max, 'tag_list' => [ hash['tag_list'], result['tag_list'].join(' ').length ].max, } end flex_width = terminal_width - columns['full_name'] - columns['author'] - (padding.length * (headers.length - 1)) tag_lists = results.map { |r| r['tag_list'] } while (columns['tag_list'] > flex_width / 3) longest_tag_list = tag_lists.sort_by { |tl| tl.join(' ').length }.last break if [ [], [term] ].include? longest_tag_list longest_tag_list.delete(longest_tag_list.sort_by { |t| t == term ? -1 : t.length }.last) columns['tag_list'] = tag_lists.map { |tl| tl.join(' ').length }.max end columns['tag_list'] = [ flex_width / 3, tag_lists.map { |tl| tl.join(' ').length }.max, ].max columns['desc'] = flex_width - columns['tag_list'] format = %w{full_name desc author tag_list}.map do |k| "%-#{ [ columns[k], min_widths[k] ].max }s" end.join(padding) + "\n" highlight = proc do |s| s = s.gsub(term, colorize(:green, term)) s = s.gsub(term.gsub('/', '-'), colorize(:green, term.gsub('/', '-'))) if term =~ /\// s end format % [ headers['full_name'], headers['desc'], headers['author'], headers['tag_list'] ] + results.map do |match| name, desc, author, keywords = %w{full_name desc author tag_list}.map { |k| match[k] } desc = desc[0...(columns['desc'] - 3)] + '...' if desc.length > columns['desc'] highlight[format % [ name.sub('/', '-'), desc, "@#{author}", [keywords].flatten.join(' ') ]] end.join end end end