I'm trying to run a .bat file on a windows server 2008 R2 64bit with IIS version 6.1 SP1.
On my local machine everything goes well but on server nothing happens, except for a process that gets created (cms.exe *32).
From my search the main problem is permissions. I read in several places that IIS for default blocks access to batch files for security reasons. I do understand the problem but in my case there would be no security issue so i would like to still run my file.
The solutions i found passed by implementing impersonation which means:
Change web.config
-> identity impersonate="true"
Change IIS Site Authentication
-> ASP.NET Impersonation Enabled
Give permissions to the file and folders
Even tried a different version of step 1
-> identity impersonate="true" userName=**********
Give permissions to the IIS User:
set allow service to interact with desktop on the IIS Admin Service
To call the batch i use the following code in C#:
private void StartPervasive(string npu)
{
try
{
ProcessStartInfo startInfo = new ProcessStartInfo(ConfigurationManager.AppSettings.Get("PervasivePath"));
//startInfo.UseShellExecute = true;
//startInfo.WorkingDirectory = ConfigurationManager.AppSettings.Get("PervasiveWorkingPath");
//startInfo.WindowStyle = ProcessWindowStyle.Normal;
//startInfo.RedirectStandardInput = true;
//startInfo.RedirectStandardError = true;
//startInfo.RedirectStandardOutput = true;
//startInfo.FileName = ConfigurationManager.AppSettings.Get("PervasivePath");
startInfo.Arguments = npu;
Process myProcess = Process.Start(startInfo);
//StreamReader sr = File.OpenText(ConfigurationManager.AppSettings.Get("PervasivePath"));
//StreamWriter sw = myProcess.StandardInput;
//while (sr.Peek() != -1)
//{
// string readed = sr.ReadLine();
// readed = readed.Replace("%1", npu);
// sw.WriteLine(readed + Environment.NewLine);
//}
//myProcess.WaitForExit();
//myProcess.Close();
}
catch (Exception ex)
{
throw ex;
}
}
It should also be of note that i tried to execute other files including .exe files but with no results.
Would appreciate any advice, help and or corrections to the steps described.
This may not be what your looking for, but may help. I would suggest you create a Scheduled Task on the Server to run the BAT file, you can set the User Permissions and then schedule when you wish to run it.
Hope this helps.
Below is a link to another Stackoverflow article that appears to have a very detailed response to the same problem.
IIS7 does not start my Exe file...
Related
I want to call an .exe that is on my Windows machine. I publish the site to a folder inside "C:\inetpub\wwwroot" and can call the API from outside. Problem is when I run the code from VS on IIS Express the exit code of the process is 0 and the exe is executed successfully, but when I call the Action Result from outside and it runs on the IIS the status code is 1 and there is obviously a problem with this process calling: Here is my code:
public async Task<ActionResult> url2img(string url)
{
Process proc = new Process();
proc.StartInfo.FileName = #"C:\Program Files\wkhtmltopdf\bin\wkhtmltoimage.exe";
proc.StartInfo.Arguments = $"--encoding utf-8 \"{url}\" {FilePath}";
proc.Start();
proc.WaitForExit();
object oJSON = new { procStatusCode = proc.ExitCode };
proc.Close();
return Json(oJSON, JsonRequestBehavior.AllowGet);
}
I found this thread, and read the proposed answer by the OP, but I cannot find "load windows profile" in my IIS and also I am not sure if this is the same issue as his? Any help?
I ran the sample and ExitCode is no longer valid after calling Close(). Hence the invalid operation.
I think, your iis user does not have privileges. may be you want to examine this link:Foo.cmd won't output lines in process (on website)
I had to set the Identity of the DefaultAppPool to LocalSystem
I'm trying to print a PDF manually through Process.Start, but it isn't working in IIS. I copied the same code in a windows form application and that worked. I already tried giving the rights to 'Network Service' user (my application pool has Network Service permission). I've also followed the steps here:
IIS7 does not start my Exe file by Process Start
string file = #"C:\test.pdf";
string printer = "TestPrinter";
string processFilename = Microsoft.Win32.Registry.LocalMachine
.OpenSubKey("Software")
.OpenSubKey("Microsoft")
.OpenSubKey("Windows")
.OpenSubKey("CurrentVersion")
.OpenSubKey("App Paths")
.OpenSubKey("AcroRd32.exe")
.GetValue(String.Empty).ToString();
var info = new ProcessStartInfo();
info.FileName = processFilename;
info.Arguments = string.Format("/h /t \"{0}\" \"{1}\"", file, printer);
info.CreateNoWindow = true;
info.WindowStyle = ProcessWindowStyle.Hidden;
info.UseShellExecute = false;
Process p = Process.Start(info);
p.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
int counter = 0;
while (!p.HasExited)
{
System.Threading.Thread.Sleep(1000);
counter += 1;
if (counter == 5) break;
}
if (!p.HasExited)
{
p.CloseMainWindow();
p.Kill();
}
Well, it took me three days and multiple ways and tools to test printing only to confirm that it's not a programming problem. It is a permission problem. When I was searching for tips, this particular problem seemed to be ongoing for more than a decade and it always happens to certain web server setups. So, here is the solution for anyone who stumbled upon the same situation as I had and save the three days of headache.
The setup:
Have a web application or service running on IIS server and you need to print some documents.
Have a network printer set up for this purpose, such as printing to a particular departmental printer within the office network.
The printing works when you are testing on localhost with your development machine.
The printing silently drops and nothing happens when deployed to the actual web server.
The reason is that a network printer is accessed in the form of \networkserver\printername and the web application account, IIS_IUSER, is not a domain account and, therefore, doesn’t have access to any network server.
Solutions:
Add the IIS_IUSER account to the domain BUT this is a very bad idea because you would need to give Internet users of your web app to have access to some network drive. Therefore, this is a no-no.
Add the printer using TCP/IP instead of setting it up as a network drive. By IP address, all local users, including the IIS_IUSER account will have access to the printer by default.
With an IP printer, no matter you use ProcessStartInfo or a third-party tool to print, it will work. Happy programming!
I'm using Pdf2Text in an ASP.NET web app. The web interface allows PDF files to be uploaded and converted to text. To convert to text, I use the C# function below, which relies on running the Pdf2Text program via the Process library.
void ExtractOCR(string input, string output)
{
ProcessStartInfo startInfo = new ProcessStartInfo();
startInfo.CreateNoWindow = true;
startInfo.UseShellExecute = true;
startInfo.FileName = Server.MapPath("ocr/Pdf2Text.exe");
startInfo.WindowStyle = ProcessWindowStyle.Hidden;
startInfo.Arguments = input + " " + output;
Process exeProcess;
using (exeProcess = Process.Start(startInfo))
{
exeProcess.WaitForExit();
}
}
I've double-checked that the input and output paths are all valid. However, when I run the web app, I get the following error.
I've tried the Just-In-Time debugger but it won't even run for some reason. The Pdf2Text is a precompiled file, I don't have it's source code. I believe this is the file's download site, but not 100% sure. I've checked online to find solutions to similar errors but none has worked.
Thank you #GraDea for suggesting to look into the pool's permissions into the web app directory, this was the solution.
The web app was located at a custom location (not the default ASP server directory of inetpub\wwwroot). After the suggestion, I tried adding the pool user to the web app's custom location, but that didn't seem to work. Next, I moved the web app to the inetpub\wwwroot location and added the pool user to the folder, restarted the site via IIS and everything is now back to normal.
For future reference to anyone, easiest fix to a similar problem is to make sure your web app is in the default IIS server directory, and that your site pool's username is added to the application folder's security permissions. I've not tried the fix for a custom location because it's not so important for me, but I'm guessing it will most likely also involve adding the necessary IIS default pool users (e.g. IIS_IUSRS) and the site pool's user.
I am running an executable process from my ASP.NET application when a user clicks a button. This process creates several files and serves them up to the end-user. I can't really see what the process is or isn't doing, but it didn't work until I specified the admin user as the application pool identity on the server. I am using IIS7.
using (var proc = new Process())
{
proc.StartInfo.FileName = Server.MapPath("~/Testing/Demo/MyExe.exe");
proc.StartInfo.Arguments = String.Format("\"{0}\"", commandFilePath);
proc.StartInfo.UseShellExecute = true;
proc.Start();
proc.WaitForExit();
}
I'm assuming that this is generally a bad thing to do. Can you give me insight into what needs to be done in order to enable this for the normal ApplicationPoolIdentity account?
Thanks!
First of all, why you need the Shell to execute it ? Isn't a console application - do you open any window ?
Second you need to redirect the input and the output.
And final, what you need to do, is to place on the directory that your script runs, permission for the user under witch your pool is run. And remove the Admin from your pool.
proc.StartInfo.UseShellExecute = false;
proc.StartInfo.CreateNoWindow = false;
proc.StartInfo.RedirectStandardError = true;
proc.StartInfo.RedirectStandardOutput = true;
proc.StartInfo.RedirectStandardInput = true;
proc.Start();
proc.StandardInput.Flush();
proc.StandardInput.Close();
proc.WaitForExit();
proc.Close();
So for example, if you add your pool to run under the UserA, then go to your directory that your program runs and add permission for the UserA to been able to execute programs on that directory. If your program also use other directories to read and write, also add permission to the UserA for that ones.
I can't really see what the process is or isn't doing
You can take a look if you use on the server the Process Explorer and see if its runs, if its close, if its stop but stay there.
It is likely a file/execution permissions issue.
Try granting execute permissions to the ApplicationPoolIdentity to ~/Testing/Dema/MyExe.exe and read permissions to commandFilePath. You mentioned that your process creates files. You will need to grant either modify or full control permissions to the ApplicationPoolIdentity on the folder where the files will be created. Here is a matrixed list of permissions.
See assign permissions to ApplicationPoolIdentity account for information on granting permissions.
The security event log should capture permission denied errors. Check there to see if you have access permission issues. The System and application logs might also contain information on the problem.
Process Explorer can also show File Access requests. Here is a technet article on troubleshooting with Process Explorer.
Whenever you run any process from an ASP.NET page, it runs under the security context of the worker process, the privilege of your app pool account. It is not like you normally running the MyExe.exe, in that case it will run using logged in account. It is because of this, your code worked when you gave Admin account to app pool.
There are many ways to solve this issue.
One of the easiest would be to change your app pool identity to Network Service and add the Network Service to permissions of the folders in which the MyExe.exe will be accessing files form.
Hope it helps.
Thank you all for your help. All I needed to do was set the StartInfo.WorkingDirectory to somewhere that I was able to write.
using (var proc = new Process())
{
proc.StartInfo.FileName = Server.MapPath("~/Testing/Demo/MyEXE.exe");
proc.StartInfo.Arguments = String.Format("\"{0}\"", commandFile);
proc.StartInfo.WorkingDirectory = savePath;
proc.Start();
proc.WaitForExit();
}
This causes the temp files to be written to a non-system folder and thus does not need any elevated permissions for the application pool.
I am working on a VPN dialer that will execute a login script when the connection is successfull using the following method.
Process p = new Process();
try
{
p.StartInfo.UseShellExecute = true;
p.StartInfo.FileName = #"\\serverName\NETLOGON\Script Test.cmd";
p.Start();
p.WaitForExit();
}
}
catch (Exception ex)
{
}
The batch file execute properly according to the logging methods in the batch file, but the drives are not acctualy mapped for the user to use. Other batch files tested (local & remote) have the same result.
I am assuming this has something to do with the application domain or UAC. The finished application will run on Viata/7 and is being tested on Windows 7.
Any help here would be greatly appreciated.
Regards
Bert
Mapped Drives are stored in a users profile. Which typically gets loaded when the person logs in. The most common way to get access to profile associated resources is to impersonate the user.
There is a relationally poor (PInvoke) example of how to do this here:
http://support.microsoft.com/kb/306158#4
But generally using mapped drives from a script is asking for trouble. IMHO :)
Hope that helps,
Jan
You can check if there is any exception happened. I see catch(exception ex) swallows you exception.