Search code examples
windowspuppetpuppet-enterprise

How to Dynamically select the path to System folder based on 32/64 bit OS with Puppet


I am automating the deployment of my web application on Windows 2008 server R2 using Puppet.

There are several steps in which I would be accessing the System folder (System32 or SysWOW64 depending on 32/64 bit OS).

Let me take one of these steps: I would access 'appcmd.exe' to Start/Stop website. When the script is running on 32-bit machine, I need to access the file at 'C:/Windows/System32/inetsrv/appcmd.exe' and when the script is running on a 64-bit machine, I need to access the file at 'C:/Windows/SysWOW64/inetsrv/appcmd.exe'

Here is the part of the script that I have written. I do not want to hard-code the path. Depending the OS, i want the path to 'appcmd.exe' to be chosen. How can I achieve this?

exec {"StopWebsite": command=> 'C:/Windows/System32/inetsrv/appcmd.exe stop site /site.name:"Default Web Site"' }


Solution

  • Not to throw you off too much, but have you looked at the puppet-iis module (formerly OpenTable's IIS module)?

    How to Use the 32-bit application (if available)

    To answer your question, this is the first time I've heard of a request to get to the 32-bit apps. The following should work with 32 or 64 bit Puppet on both 32 and 64 bit Operating Systems:

    exec {'StopWebsite': 
      path    => 'C:/Windows/SysWOW64/inetsrv;C:/Windows/System32/inetsrv',
      command => 'appcmd.exe stop site /site.name:"Default Web Site"',
    }
    

    It works because it checks for the command in C:\Windows\SysWOW64 first before moving on to C:\Windows\system32. This allows it to fall through to the correct 32-bit appcmd.exe when it runs.

    How to Use the 64-bit application (if available)

    For others, if you are always trying to get to the 64 bit processes and your on Puppet 3.7.3 or later, use the $system32 fact. This works no matter if you are using a 64-bit or 32-bit version of Puppet.

    exec {'somefunction': 
      command => "$system32\\cmd.exe /c some command",
    }
    

    Or you can also try the opposite trick, set the path order so that it will get sysnative first with a fallback to system32.

    exec {'somefunction': 
      path    => 'C:/Windows/sysnative;C:/Windows/System32',
      command => 'cmd.exe /c some command',
    }
    

    Keep the Rest of the Path Intact

    If you need to keep the rest of the path, just append $path to the end of the string, but specify it with double quotes:

    path => "C:\\Windows\\sysnative;C:\\Windows\\System32;$::path",
    

    You will probably be fine with forward slashes, but the rest of $path comes in with backslashes, so I didn't want to confuse the handler.