windows系統,如何創建任務計划程序


  在windows系統中,我們總能感受到一些開機或者登錄后,就會彈出軟件更新的小彈窗,或者其他軟件彈出的各種小窗口。如何實現這種功能呢?

  實現開機或者登錄后檢測更新、彈出小彈窗,有兩種方法。一種是寫一個小程序,然后加入到開機自啟注冊表中,讓系統運行它;另一種是寫一個任務計划程序,由它控制更新或者執行其他任務。

  甚至,如果開機自啟的小程序需要管理員權限運行,而程序又沒有windows認證的安全證書,開機自啟都不會啟動它。但任務計划程序是直接運行這個程序的,即使需要管理員權限,因為創建任務計划程序本就需要管理員權限創建。

         

 

 

  創建一個任務計划程序,很簡單,首先需要我們引入一個Microsoft.Win32.TaskScheduler.dll(下載地址)。

  引入dll后,我們需要用到TaskService類,它能夠管理計算機上的服務。

1、TaskService的簡單用法

/// <summary>
/// 獲取所有任務
/// </summary>
public static TaskCollection GetAllTasks()
{
    TaskService ts = new TaskService();
    var folder = ts.GetFolder("\\");
    var tasks_exists = folder.GetTasks();
    folder.Dispose();
    ts.Dispose();
    return tasks_exists;
}

/// <summary>
/// 檢查任務是否存在
/// </summary>
/// <param name="taskName"></param>
/// <returns></returns>
public static bool IsExists(string taskName)
{
    var isExists = false;
    TaskCollection tasks_exists = GetAllTasks();
    for (int i = 0; i < tasks_exists.Count; i++)
    {
        var task = tasks_exists[i];
        if (task.Name.Equals(taskName))
        {
            isExists = true;
            break;
        }
    }
    return isExists;
}

/// <summary>
/// 刪除指定任務
/// </summary>
/// <param name="taskName"></param>
public static void DeleteTask(string taskName)
{
    TaskService ts = new TaskService();
    var folder = ts.GetFolder("\\");
    folder.DeleteTask(taskName);
    folder.Dispose();
    ts.Dispose();
}

2、創建一個任務計划程序

  創建一個任務計划程序,首先需要獲得當前計算機的任務計划程序集,然后定義一個任務。直接new一個TaskService對象,然后調用TaskService 對象的方法NewTask()獲取到一個TaskDefinition的對象,該對象將是我們設置任務信息的核心操作者。

  1. TaskDefinition 的 RegistrationInfo,就是我們看到的任務里常規的顯示信息,注入創建者、創建時間、版本、描述等等信息;
  2. TaskDefinition 的 Triggers 定義什么時候觸發程序執行,開機后?登錄后?還是延遲啟動?等等不同的類型,這就是任務里的觸發器。 不同的觸發器,內容不一樣(不詳述),定義好Trigger,然后將對象加入TaskDefinition 的Triggers集合里。當然,一個任務也可以有多個觸發器;
  3. TaskDefinition 的 Actions 將定義觸發器觸發后,執行什么操作,比如啟動程序?下載數據?上報數據?還是其他的。同理,Action也可以有多個。
  4. TaskDefinition 的 Settings 可以配置任務的條件和設置。比如,某些操作必須要先接通電源。
  5. 最后,只需要調用TaskService的RootFolder.RegisterTaskDefinition,注冊該任務對象,就可以了。

  下面是我簡單定義了一個用戶登錄則啟動的一個示例:

 /// <summary>
 /// 創建指定任務
 /// </summary>
 /// <param name="taskName"></param>
 /// <param name="path"></param>
 /// <param name="description"></param>
 /// <param name="creator"></param>
 /// <param name="delay">延時啟動時間</param>
 /// <returns></returns>
 public static TaskState CreateTaskScheduler(string taskName, string path, string description = "", string creator = "", TimeSpan? delay = null)
 {
     try
     {
         if (IsExists(taskName))
         {
             DeleteTask(taskName);
         }

         TaskService service = new TaskService();
         TaskDefinition definition = service.NewTask();
         definition.RegistrationInfo.Author = creator;
         definition.RegistrationInfo.Description = description;
         definition.RegistrationInfo.Version = new Version(1, 0, 0);
         definition.RegistrationInfo.Date = DateTime.Now;
         //開機自啟
         //BootTrigger bootTrigger = new BootTrigger();
         //// bootTrigger.StartBoundary = Convert.ToDateTime(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"));
         //bootTrigger.Enabled = true;
         //if (delay.HasValue)
         //{
         //    bootTrigger.Delay = delay.Value;
         //}
         ////設置重復任務間隔時間
         ////bootTrigger.Repetition.Interval = TimeSpan.FromDays(1);
         //td.Triggers.Add(bootTrigger);
         //用戶登錄時啟動
         LogonTrigger logonTrigger = new LogonTrigger();
         //logonTrigger.StartBoundary = Convert.ToDateTime(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"));
         logonTrigger.Enabled = true;
         if (delay.HasValue)
         {
             logonTrigger.Delay = delay.Value;
         }
         //設置重復任務間隔時間
         //logonTrigger.Repetition.Interval = TimeSpan.FromDays(1);
         definition.Triggers.Add(logonTrigger);


         definition.Actions.Add(new ExecAction(path, "", null));

         definition.Principal.RunLevel = TaskRunLevel.Highest;
         definition.Principal.UserId = "Administrators";
         definition.Principal.LogonType = TaskLogonType.InteractiveToken;

         //td.Settings.ExecutionTimeLimit = ; //運行任務時間超時停止任務嗎?
         definition.Settings.DisallowStartIfOnBatteries = false;//只有在交流電源下才執行
         definition.Settings.RunOnlyIfIdle = false;//僅當計算機空閑下才執行
         definition.Settings.Enabled = true;
         definition.Settings.AllowDemandStart = true;
         definition.Settings.AllowHardTerminate = true;


         var task = service.RootFolder.RegisterTaskDefinition(taskName, definition,
             TaskCreation.CreateOrUpdate,
             "Administrators", null,
             TaskLogonType.Group,
             "");
         //task.Run();
         return task.State;

     }
     catch (Exception ex)
     {
         throw ex;
     }
 }

3、創建一個任務

  由於任務是可以繞開安全檢查的,但創建一個任務是繞不開的,因此,創建一個任務,需要使用管理員權限。

  首先,檢測管理員權限,然后才是創建任務。 

WindowsIdentity identity = WindowsIdentity.GetCurrent();
WindowsPrincipal principal = new WindowsPrincipal(identity);
bool isAdmin = principal.IsInRole(WindowsBuiltInRole.Administrator);
void CreateTask()
{
    string taskName = "NigleAutoStart";
    var creator = "Y&Z";
    var path = @"D:\WpfApp1.exe";//任務動作為啟動D盤下的程序
    var description = "開機自啟";
    Console.WriteLine("設置任務");
    var state = SystemTaskScheduler.CreateTaskScheduler(taskName, path, description, creator);

    Console.WriteLine($"任務設置成功:{state}");
    if (state == Microsoft.Win32.TaskScheduler.TaskState.Running)
    {
        System.Threading.Thread.Sleep(2000);
        SystemTaskScheduler.DeleteTask(taskName);
        Console.WriteLine("刪除任務");
    }
}

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM