2013-05-03 158 views
5

我有一个Windows计划任务,每小时运行一次数据库导入过程,但是我希望用户能够通过点击按钮来按计划启动它一个ASP.net仪表板(在Windows Server 2003的IIS6上运行)。从ASP.net运行Windows计划任务

下完全在后台代码...

var proc = new Process 
      { 
       StartInfo = 
        { 
         UseShellExecute = false, 
         FileName = @"C:\Windows\System32\schtasks.exe", 
         Arguments = "/run /tn Loader", 
         RedirectStandardError = true, 
         RedirectStandardOutput = true, 
         CreateNoWindow = true 
        } 
      }; 
proc.Start(); 
proc.WaitForExit(); 

...但只有当应用程序池标识设置为本地系统(不理想!)。如果我将其作为网络服务保留,则任务不会启动。所以这可能是一个权限问题。

有没有办法ASP.net可以启动服务器上的计划任务,而无需作为本地系统运行应用程序?如果没有,那么有什么好的选择?

更新:如果没有人知道,我想这是不可能的,所以我会去我的想法让我的Web应用程序向数据库表写入请求(加倍作为审计日志)并创建第二个任务轮询该表并启动主要任务。

+0

为什么你不调用这个任务将在你的web应用程序中调用什么?你为什么要运行这个任务,而不是任务的目标? – Kousha 2013-08-26 11:19:10

+0

好问题。 1我需要以特定用户身份运行任务,并且2它不能与小时计划任务同时运行,如果任务已手动启动,则Windows计划程序无法启动。不过,这不是我详细探讨过的选项。 – Chris 2013-08-27 07:25:43

回答

1

您需要Windows中的管理员用户。此代码将帮助你调用任务:

var proc = new Process 
      { 
       StartInfo = 
        { 
         UseShellExecute = false, 
         FileName = @"C:\Windows\System32\schtasks.exe", 
         Arguments = "/run /tn Loader", 
         UserName = "myAdminUser", //NEW 
         Password = "Pass", //NEW 
         RedirectStandardError = true, 
         RedirectStandardOutput = true, 
         CreateNoWindow = true 
        } 
      }; 
proc.Start(); 
proc.WaitForExit(); 

如果您应用需要为系统帐户运行,你可以使用这个参数:

如果/ RU用户名和/ RP密码参数匹配当前登录的用户 ,该任务将以交互方式运行(可见于前景 )。

对于系统帐户,/ RU用户名可以写为“”,“NT AUTHORITY \ SYSTEM”或“SYSTEM”,不需要密码。系统 帐户具有对本地计算机的完全访问权限,但在网络上没有任何其他计算机(或映射驱动器)的 权限。

来源:http://ss64.com/nt/schtasks.html

+0

ProcessStartInfo.Password是SecureString类型而不是字符串,因此此代码不能编译。 – Dan 2015-09-01 10:37:13

1

更新你的计划任务触发关闭特定事件。然后让您的网站在单击按钮时记录该事件 - 从而启动您的计划任务。

例: 在我安装我创建一个事件日志来源为我的计划,因为创建源需要管理员权限(you can also use the command line to create the source

if (EventLog.SourceExists("MyApp")) 
    { 
     EventLog.CreateEventSource("MyApp", "Application"); 
    } 

然后在我的申请,我创建了当一个事件日志项按钮被点击。

private void btnOpenOtherApp_Click (object sender, EventArgs e) 
{ 
    try 
    { 
     var log = new EventLog 
     { 
      Source = "MyApp" 
     }; 
     log.WriteEntry("Start MyOtherApp", EventLogEntryType.Information, 1337); 
    } 
    catch (Exception ex) 
    { 
     ... 
    } 
} 

而且任务计划程序设置为在事件记录时打开MyOtherApp。 Event viewer

+0

他会“需要注册表更改”以获得正确的写入权限。 – highwingers 2014-10-21 05:46:38

+1

?我的不是。如果你设置log.source =“.NET运行时”,你会没事的。虽然,我将它设置为我的应用程序名称,因为我将安装程序设置为将应用程序添加为事件日志源。如果你愿意,我会发布一些代码。 – basher 2014-10-21 13:49:05

+0

是的,你是对的。我只是试了一下,它工作。不过,我想知道如何创建一个新的源...做一些代码。 – highwingers 2014-10-22 06:00:28

0

如果使用第三方调度程序服务,如Quartz.NET不是一个选项,更改权限不允许或者(在任何情况下,不是一个好主意),另一种可能性是写一个助手Windows服务的桥梁ASP.NET应用程序和Windows调度程序之间。你将存储的任务列表中的一个DB和事件的顺序是这样的:

  1. 当你需要运行任务,从ASP.NET GUI您为任务设置标志在DB
  2. 帮助服务按预定时间运行,以给定间隔检查数据库 - 查看标志,启动任务,重置标志。

哦,并且有一些库(例如http://taskscheduler.codeplex.com/等)封装了Window Task Scheduler,因此您不必直接执行它们,而是以一种很好的管理方式执行它们。