Skip to content
This repository has been archived by the owner on May 14, 2021. It is now read-only.

Ignore non-zero exit codes on outdated #4

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
54 changes: 43 additions & 11 deletions lib/poise_javascript/resources/node_package.rb
Original file line number Diff line number Diff line change
Expand Up @@ -125,7 +125,7 @@ def check_package_versions(resource)
# here so you get slow behavior, sorry.
requested_packages = Set.new(Array(resource.package_name))
if npm_version?('>= 1.3.16') && version_data.any? {|pkg_name, _pkg_vers| requested_packages.include?(pkg_name) }
outdated = npm_shell_out!('outdated') || {}
outdated = npm_shell_out('outdated') || {}
version_data.each do |pkg_name, pkg_vers|
pkg_vers[:candidate] = if outdated.include?(pkg_name)
outdated[pkg_name]['wanted']
Expand Down Expand Up @@ -195,31 +195,63 @@ def remove_package(name, version)

private

# Run an npm command.
# Run an npm command and raise errors for non-zero exit codes.
#
# @param subcmd [String] Subcommand to run.
# @param args [Array<String>] Command arguments.
# @param parse_json [Boolean] Parse the JSON on stdout.
# @return [Hash]
def npm_shell_out!(subcmd, args=[], parse_json: true)
out = javascript_shell_out!(cmd(subcmd, args), cwd: new_resource.path, group: new_resource.group, user: new_resource.user, environment: {'PATH' => new_path})
return parse_json(out) if parse_json
out
end

# Run an npm command and do not raise errors (for npm outdated, which
# always returns exit code 1 if there are outdated packages).
#
# @param subcmd [String] Subcommand to run.
# @param args [Array<String>] Command arguments.
# @param parse_json [Boolean] Parse the JSON on stdout.
# @return [Hash]
def npm_shell_out(subcmd, args=[], parse_json: true)
out = javascript_shell_out(cmd(subcmd, args), cwd: new_resource.path, group: new_resource.group, user: new_resource.user, environment: {'PATH' => new_path})
return parse_json(out) if parse_json
out
end

# Build a proper npm command for given arguments.
#
# @param subcmd [String] Subcommand to run.
# @param args [Array<String>] Command arguments.
# @return [String]
def cmd(subcmd, args)
cmd = [new_resource.npm_binary, subcmd, '--json']
# If path is nil, we are in global mode.
cmd << '--global' unless new_resource.path
# Add the rest.
cmd.concat(args)
cmd
end

# Return the proper path for running npm commands.
#
# @return [String]
def new_path
# If we are in global mode, cwd will be nil so probably just fine. Add
# the directory for the node binary to $PATH for post-install stuffs.
new_path = [::File.dirname(new_resource.javascript), ENV['PATH'].to_s].join(::File::PATH_SEPARATOR)
out = javascript_shell_out!(cmd, cwd: new_resource.path, group: new_resource.group, user: new_resource.user, environment: {'PATH' => new_path})
if parse_json
# Parse the JSON.
if out.stdout.strip.empty?
{}
else
Chef::JSONCompat.parse(out.stdout)
end
end

# Parse JSON for an npm javascript_shell_out command.
#
# @param out [Hash] The shell_out output to be parsed.
# @return [String]
def parse_json(out)
if out.stdout.strip.empty?
{}
else
out
Chef::JSONCompat.parse(out.stdout)
end
end

Expand Down
15 changes: 11 additions & 4 deletions test/spec/resources/node_package_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -97,11 +97,18 @@
let(:new_resource) { double('new_resource', path: nil, javascript: '/node', npm_binary: '/npm', user: nil, group: nil) }
let(:test_provider) { described_class.new(new_resource, double(resource_collection: nil)) }

def stub_javascript_shell_out(cmd, ret, **options)
def default_options
default_options = {cwd: nil, user: nil, group: nil, environment: {'PATH' => "/:#{ENV['PATH']}"}}
end

def stub_javascript_shell_out(cmd, ret, **options)
allow(test_provider).to receive(:javascript_shell_out!).with(cmd, default_options.merge(options)).and_return(double(stdout: ret))
end

def stub_outdated(ret, **options)
allow(test_provider).to receive(:javascript_shell_out).with(%w{/npm outdated --json --global}, default_options.merge(options)).and_return(double(stdout: ret))
end

describe '#load_current_resource' do
let(:new_resource) do
PoiseJavascript::Resources::NodePackage::Resource.new('mypkg', nil)
Expand Down Expand Up @@ -179,7 +186,7 @@ def stub_javascript_shell_out(cmd, ret, **options)

before do
stub_javascript_shell_out(%w{/npm list --json --global --depth 0}, npm_list_out)
stub_javascript_shell_out(%w{/npm outdated --json --global}, <<-EOH)
stub_outdated(<<-EOH)
{
"bower": {
"current": "1.3.12",
Expand All @@ -200,7 +207,7 @@ def stub_javascript_shell_out(cmd, ret, **options)

before do
stub_javascript_shell_out(%w{/npm list --json --global --depth 0}, npm_list_out)
stub_javascript_shell_out(%w{/npm outdated --json --global}, <<-EOH)
stub_outdated(<<-EOH)
{
"bower": {
"current": "1.3.12",
Expand All @@ -222,7 +229,7 @@ def stub_javascript_shell_out(cmd, ret, **options)

before do
stub_javascript_shell_out(%w{/npm list --json --global --depth 0}, npm_list_out)
stub_javascript_shell_out(%w{/npm outdated --json --global}, '')
stub_outdated('')
end

its([:version]) { is_expected.to eq '1.3.12' }
Expand Down