Reputation: 2929
The initial problem I Was trying to solve was that chefDK version of ruby wasn't showing up because it was at the end of the PATH
environmental variable, so I have created a block of code to check and then add if it doesn't find it.
powershell_script "add_chefdk_bin_to_shell" do
code '$oldPath=(Get-ItemProperty -Path \'Registry::HKEY_LOCAL_MACHINE\System\CurrentControlSet\Control\Session Manager\Environment\' -Name PATH).Path
$newPath= \'C:\opscode\chefdk\embedded\bin;\' + $oldPath
Set-ItemProperty -Path \'Registry::HKEY_LOCAL_MACHINE\System\CurrentControlSet\Control\Session Manager\Environment\' -Name PATH –Value $newPath
'
only_if { `powershell $a = $Env:Path; $a -match 'C:\\opscode\\chefdk\\embedded\\bin'` == "False" }
end
Except when berk shelf runs (to publish the chef cookbook to our chef server) it spits out this error:
**E, [2014-10-24T11:33:55.771484 #2916] ERROR -- : Cookbook file recipes/install.rb has a ruby syntax error:
E, [2014-10-24T11:33:55.771484 #2916] ERROR -- : c:/path/to/cookbook/root/recipes/install.rb:25: invalid multibyte char (US-ASCII)
E, [2014-10-24T11:33:55.771484 #2916] ERROR -- : c:/path/to/cookbook/root/recipes/install.rb:23: invalid multibyte char (US-ASCII)
E, [2014-10-24T11:33:55.771484 #2916] ERROR -- : c:/path/to/cookbook/root/recipes/install.rb:23: syntax error, unexpected $end, expecting keyword_end
E, [2014-10-24T11:33:55.771484 #2916] ERROR -- : ...ger\Environment\' -Name PATH –Value $newPath
E, [2014-10-24T11:33:55.771484 #2916] ERROR -- : ... ^
E, [2014-10-24T11:33:55.771484 #2916] ERROR -- : Ridley::Errors::CookbookSyntaxError: Invalid ruby files in cookbook: gg-web-opsboard (1.0.177).**
This is very-much beginning to frustrate me, I'm only doing this in the first place because chefDK isn't being used as the default ruby (which is screwing a bunch of other stuff up).
There is a secondary issue, if I look at the path, I can clearly see C:\opscode\chefdk\embedded\bin
at the end, so why does:
powershell $a = $Env:Path; $a -match 'C:\\opscode\\chefdk\\embedded\\bin'
Register as false?
EDIT:
I tried what @acro444 said but I'm still getting errors:
E, [2014-10-24T12:36:15.642147 #1932] ERROR -- : Cookbook file recipes/install.rb has a ruby syntax error:
E, [2014-10-24T12:36:15.642147 #1932] ERROR -- : c:/path/to/cookbook/root/recipes/install.rb:24: Invalid escape character syntax
E, [2014-10-24T12:36:15.642147 #1932] ERROR -- : ...ry::HKEY_LOCAL_MACHINE\System\CurrentControlSet\Control\Sess...
E, [2014-10-24T12:36:15.642147 #1932] ERROR -- : ... ^
E, [2014-10-24T12:36:15.642147 #1932] ERROR -- : c:/path/to/cookbook/root/recipes/recipes/install.rb:24: Invalid escape character syntax
E, [2014-10-24T12:36:15.642147 #1932] ERROR -- : ...HINE\System\CurrentControlSet\Control\Session Manager\Enviro...
E, [2014-10-24T12:36:15.642147 #1932] ERROR -- : ... ^
E, [2014-10-24T12:36:15.642147 #1932] ERROR -- : c:/path/to/cookbook/root/recipes/recipes/install.rb:26: Invalid escape character syntax
E, [2014-10-24T12:36:15.642147 #1932] ERROR -- : ...ry::HKEY_LOCAL_MACHINE\System\CurrentControlSet\Control\Sess...
E, [2014-10-24T12:36:15.642147 #1932] ERROR -- : ... ^
E, [2014-10-24T12:36:15.642147 #1932] ERROR -- : c:/path/to/cookbook/root/recipes/install.rb:26: Invalid escape character syntax
E, [2014-10-24T12:36:15.642147 #1932] ERROR -- : ...HINE\System\CurrentControlSet\Control\Session Manager\Enviro...
E, [2014-10-24T12:36:15.642147 #1932] ERROR -- : ... ^
E, [2014-10-24T12:36:15.642147 #1932] ERROR -- : c:/path/to/cookbook/root/recipes/install.rb:26: invalid multibyte char (US-ASCII)
E, [2014-10-24T12:36:15.642147 #1932] ERROR -- : c:/path/to/cookbook/root/recipes/install.rb:23: syntax error, unexpected $end, expecting tSTRING_CONTENT or tSTRING_DBEG or tSTRING_DVAR or tSTRING_END
I did the quadruple backslash escapething you did on all the backslashes and that reduced the error to just :
syntax error, unexpected $end, expecting tSTRING_CONTENT or tSTRING_DBEG or tSTRING_DVAR or tSTRING_END
I removed all trailing white space but that didn't fix it, currently my herdoc looks like:
code <<-EOF
$oldPath=(Get-ItemProperty -Path 'Registry::HKEY_LOCAL_MACHINE\\\\System\\\\CurrentControlSet\\\\Control\\\\Session Manager\\\\Environment' -Name PATH).Path
$newPath='C:\\\\opscode\\\\chefdk\\\\embedded\\\\bin;' + $oldPath
Set-ItemProperty -Path 'Registry::HKEY_LOCAL_MACHINE\\\\System\\\\CurrentControlSet\\\\Control\\\\Session Manager\\\\Environment' -Name PATH –Value $newPath
EOF
Upvotes: 0
Views: 1621
Reputation: 26
If you want, you can skip the guard block, and move some of the operation to ruby like this:
ruby_block "chefdk_path_check" do
block do
current_path = ENV['PATH'].split(';')
chefdk_path = 'C:\\opscode\\chefdk\\embedded\\bin'
current_path.delete_if { |path| path == chefdk_path }
new_path = current_path.unshift(chefdk_path)
`Powershell -Command Set-ItemProperty -Path 'Registry::HKEY_LOCAL_MACHINE\\System\\CurrentControlSet\\Control\\Session Manager\\Environment' -Name PATH –Value '#{new_path}'`
end
end
This will check every time, remove any existing entry (if it is in the wrong position in the path), and add the desired entry to the beginning. No duplicates and a lot less escaping to worry about!
Upvotes: 1
Reputation: 22821
Try structuring the block as follows:
powershell_script "add_chefdk_bin_to_shell" do
code <<-EOF
$oldPath=(Get-ItemProperty -Path 'Registry::HKEY_LOCAL_MACHINE\System\CurrentControlSet\Control\Session Manager\Environment' -Name PATH).Path
$newPath='C:\opscode\chefdk\embedded\bin;' + $oldPath
Set-ItemProperty -Path 'Registry::HKEY_LOCAL_MACHINE\System\CurrentControlSet\Control\Session Manager\Environment' -Name PATH –Value $newPath
EOF
only_if { `powershell -command "$Env:Path -match 'C:\\\\opscode\\\\chefdk\\\\embedded\\\\bin'".strip }` == "False"
end
Your only_if
guard has a couple of problems. Firstly, powershell itself requires the paths to be escaped - \\
, therefore you need to double escape in the ruby command.
Secondly, the condition will never be met because the powershell command also includes the newline character on the end of the string, and you weren't matching for that. Hence add the strip
to the end of the command. You can test that using irb:
irb> `powershell -command "$Env:Path -match 'C:\\\\opscode\\\\chefdk\\\\embedded\\\\bin'"`
=> "True\n"
You may even be able to swap out the guard as it's written altogether and use the built in interpreter:
guard_interpreter :powershell_script
not_if "$Env:Path -match 'C:\\\\opscode\\\\chefdk\\\\embedded\\\\bin'"
Have a good read of this link.
Upvotes: 0