title: Invoking Powershell via C# in a web application - issues with app pool identity
body: <p>I have written some stuff to execute Powershell via C# using RunspaceFactory. </p>
  
  <p>I am loading the default Powershell profile like this: </p>
  
  <pre><code>   Runspace runspace = RunspaceFactory.CreateRunspace();
     runspace.Open();
     string scriptText = @". .\" + scriptFileName + "; " + command;
     Pipeline pipeline = runspace.CreatePipeline(scriptText);
  </code></pre>
  
  <p>Command = a function from the profile i know works.</p>
  
  <p>All of this Powershell stuff is wrapped in Impersonator. </p>
  
  <p>For the avoidance of doubt, $profile = C:\Users\Administrator\Documents\WindowsPowerShell\Microsoft.PowerShell_profile.ps1</p>
  
  <p>This is a web application running under IIS 7.5</p>
  
  <p>If my IIS app runs under the 'administrator' account, it works. Under any other account it throws the error: </p>
  
  <blockquote>
    <p>"The term '.\Microsoft.PowerShell_profile.ps1' is not recognized as the name of a cmdlet, function, script file, or operable program. Check the spelling of the name, or if a path was included, verify that the path is correct and try again."</p>
  </blockquote>
  
  <p>As I am impersonating the 'administrator' account I assumed the location would be correct. </p>
  
  <p>Some logging with an invoked 'get-location' reports the directory is what it should be. </p>
  
  <p>Out of bloody mindedness i tried to force it with:</p>
  
  <pre><code>  System.Environment.CurrentDirectory = dir;
  </code></pre>
  
  <p>... and also an attempt at an invoked 'set-location'. These work, but if I invoke 'get-location' from a runspace it reports the same directory as before (the correct one). </p>
  
  <p>I thought that, perhaps, there might be a problem with the impersonation, so i wrote some tests that touch the file system in ways the app pool shouldn't be able to do. These work. </p>
  
  <p>I also checked this: </p>
  
  <pre><code>string contextUserName = System.Security.Principal.WindowsIdentity.GetCurrent().Name;
  </code></pre>
  
  <p>Which reports the correct user both when code is 'wrapped' in impersonator, and when it is executed via the app pool identity.  Then I got desperate and tried invoke: </p>
  
  <pre><code> @"cmd /c dir"
  </code></pre>
  
  <p>... (and also get-Childitem). Both commands return:</p>
  
  <pre><code>{}
  </code></pre>
  
  <p>...when running under the app pool identity (regardless of impersonation), but a full and accurate directory listing of the correct directory when the app pool is running as 'administrator'.</p>
  
  <p>I am sure I am missing something stupid and fundamental here, if anyone could give me some guidance on where I've made a mistake in my thinking (and code), that would be great. </p>