Symbian Developers and device creators can use the task scheduler APIs to develop programs with scheduling capabilities. Programs may need task scheduling capabilities to support scheduling options that may be required for a phone user, another program or a system server.
For example, a phone user can use the alarm option of a clock application to schedule an alarm to be triggered every day at 5:00 A.M.
RScheduler iScheduler; User::LeaveIfError(iScheduler.Connect());
taskexecutor.cpp
topic
in theTaskSchedulerExample:
Using Task Scheduler for Creating and Executing Tasks section.
RScheduler iScheduler; TFileName fileName; ... //A priority value const TInt priority = 3; ... User::LeaveIfError(iScheduler.Register(filename, priority));
Note: Task scheduler supports only the execution of Symbian platform executables. The
aFileName
parameter can include a path but
must not include a file extension. fileName
can be minimalTaskHandler
.
Note that in the presence of platform security all EXEs are located in the \sys\bin
folder
and as a consequence of this, the path of an EXE (only the drive letter) is
not needed.
... TSchedulerItemRef& aRef; //Array to hold the schedule entries CArrayFixFlat<TScheduleEntryInfo2>* cSchEntryInfoArray; cSchEntryInfoArray = new CArrayFixFlat<TScheduleEntryInfo2>(1); CleanupStack::PushL(cSchEntryInfoArray); // Create an hourly schedule TScheduleEntryInfo2 entry1; //Sets the date and time for the schedule as Jan 1st, 2010, 08:00 am TDateTime datetime2(2010, EJanuary, 1, 8, 0, 0, 0); TTsTime time2(datetime2, ETrue); //Set the first instance when the entry will cause the execution of tasks. entry1.SetStartTime(time2); // Set the interval between execution of tasks // Here the interval is 2 hours because the interval type is hourly. const TInt interval = 2; entry1.SetInterval(interval); // Set the type of interval used between due times for the scheduled entry entry1.SetIntervalType(TIntervalType(EHourly)); // Set the period for which the entry is valid. After 8 hours the // tasks associated with the entry will not be eligible for execution. const TInt eightHours = 480; // in minutes entry1.SetValidityPeriod(TTimeIntervalMinutes(eightHours)); cSchEntryInfoArray->AppendL(entry1); //create the time-based persistent schedule User::LeaveIfError(iScheduler.CreatePersistentSchedule(aRef, *cSchEntryInfoArray)); CleanupStack::PopAndDestroy(cSchEntryInfoArray); ...
condtion1
and condtion2
are
satisfied. By default, the schedule is set to start on December 10th, 2009
at 09:00 A.M., if the condition set is not met.
... TSchedulerItemRef& aRef; //Array to hold the schedule conditions CArrayFixFlat<TTaskSchedulerCondition>* cTaskScheCondArray; //Condition list to hold a set of conditions CSchConditionArray conditionList = new (ELeave) CSchConditionArray(2); CleanupStack::PushL(conditionList); //set the first condition TTaskSchedulerCondition condition1; //UID of the publish and subscribe category for condition1 const TUid KPubSubsPersistCondCategUid1 = TUid::Uid(0x102F7784); //Key of the publish and subscribe category for condition2 const TInt KPubSubsPersistCondKey1 = 1; condition1.iCategory = KPubSubsPersistCondCategUid1; condition1.iKey = KPubSubsPersistCondKey1; condition1.iState = 10; condition1.iType = TTaskSchedulerCondition::EEquals; conditionList->AppendL(condition1); //set the second condition TTaskSchedulerCondition condition2; //UID of the publish and subscribe category for condition2 const TUid KPubSubsPersistCondCategUid2 = TUid::Uid(0x103F7784); //Key of the publish and subscribe category for condition2 const TInt KPubSubsPersistCondKey2 = 1; condition2.iCategory = KPubSubsPersistCondCategUid2; condition2.iKey = KPubSubsPersistCondKey2; condition2.iState = 20; condition2.iType = TTaskSchedulerCondition::ENotEquals; conditionList->AppendL(condition2); //Set the date and time for the schedule as Dec 10th, 2009, 09:00 am TDateTime datetime2(2009, EDecember, 10, 9, 0, 0, 0); TTsTime time2(datetime2, EFalse); //create the condition-based persistent schedule iScheduler.CreatePersistentSchedule(aRef, *conditionList, time2); CleanupStack::PopAndDestroy(); // conditionList
... TSchedulerItemRef ref; // Array that holds the schedule entries CArrayFixFlat<TScheduleEntryInfo2>* cSchEntryInfoArray; cSchEntryInfoArray = new CArrayFixFlat<TScheduleEntryInfo2>(1); CleanupStack::PushL(cSchEntryInfoArray); // Create a schedule entry TScheduleEntryInfo2 entry; TTime now; // Set the date and time of this TTime to the universal time. now.UniversalTime(); // Assign an offset of 15 seconds. TInt offset = 15; now += TTimeIntervalSeconds(offset); // Constructs a TTsTime with a TTime object. // ETrue indicates that TTsTime is UTC based time TTsTime time(now, ETrue); // Set the above time as the first time at which // the entry will cause execution of tasks. entry.SetStartTime(time); // Set the type of interval used between due times for scheduled entry entry.SetIntervalType(TIntervalType(EHourly)); // Set the period for which the entry is valid. // After 2 hours the tasks associated with the entry will not be eligible for execution TInt validity = 120; entry.SetValidityPeriod(TTimeIntervalMinutes(validity)); // Set the interval between execution of tasks // Here the interval is 1 hour because the interval type is hourly. entry.SetInterval(1); //Add the schedule entry to the array cSchEntryInfoArray->AppendL(entry); // Create a transient task to be scheduled TTaskInfo taskInfo; // Task id const TInt tId = 0; taskInfo.iTaskId = tId; // The task repeats just once const TInt numberOfRepeats = 1; taskInfo.iRepeat = numberOfRepeats; // Task priority set by the client. // Where a client has two tasks with different priorities, // the task with the higher priority will be executed first. const TInt priority = 2; taskInfo.iPriority = priority; _LIT(KScheduleType," transient schedule"); const TDesC* transient = &KScheduleType; HBufC* data = transient->AllocLC(); // Create the transient time-based schedule User::LeaveIfError(iScheduler.ScheduleTask(taskInfo, *data, ref, *cSchEntryInfoArray)); ...Important: The task scheduler does not notify a client if a scheduled task fails to execute successfully. Clients can however use the notification mechanism of the Log Engine to get some notification and information of the error condition that caused the task to fail.
Errors can occur when the task scheduler prepares to create and run a task process. The most likely error is an out of memory error. The task scheduler logs the error to the system log with type KLogTaskSchedulerEventTypeUid. The task or schedule is not retried.
If the task process is created successfully, but it exits with an error, the task scheduler logs the process exit reason to the system log, also with type KLogTaskSchedulerEventTypeUid.
condition1
is
met. By default, the schedule is set to start on December 10th, 2009 at 09:00
A.M., if the condition set is not met.
... TSchedulerItemRef ref2; //Array that holds the conditions CArrayFixFlat<TTaskSchedulerCondition>* CSchConditionArray; CSchConditionArray conditionList = new (ELeave) CSchConditionArray(1); CleanupStack::PushL(conditionList); //set the condition TTaskSchedulerCondition condition1; //UID of the publish and subscribe category for condition1 const TUid KPubSubsTransCondCategUid1 = TUid::Uid(0x102F7785); //Key of the publish and subscribe category for condition1 const TInt KPubSubsTransCondKey1 = 1; condition1.iCategory = KPubSubsTransCondCategUid1; condition1.iKey = KPubSubsTransCondKey1; condition1.iState = 10; condition1.iType = TTaskSchedulerCondition::EEquals; conditionList->AppendL(condition1); // Associate a task with the condition-based schedule TTaskInfo taskInfo2; _LIT(KTransSchedTaskName, "Transient - Condition-Based"); _LIT(KTransSchedTaskData2, "Task data for transient schedule"); taskInfo2.iName = KTransSchedTaskName; taskInfo2.iPriority = 2; taskInfo2.iRepeat = 0; // Create some data associated with this task HBufC* taskTransSchedData = KTransSchedTaskData2().AllocLC(); //set the default time at which you want the transient condition-based //schedule to start, if no conditions are met // sets the date and time as Jan 1st, 2010, 10:01 am TDateTime datetime2(2010, EJanuary, 1, 10, 1, 0, 0); TTsTime defaultRuntime(datetime2, ETrue); // 10:01 am // Create the transient condition-based schedule User::LeaveIfError(iScheduler.ScheduleTask(taskInfo2, *taskTransSchedData, ref2, *conditionList, defaultRuntime)); CleanupStack::PopAndDestroy(2); // taskTransSchedData, conditionList ...
Note: Schedules can be either persistent or transient. Persistent schedules have schedule information and any corresponding task data persisted to the disk.
This step applies only, if you have already created a persistent schedule.
For more information about the effects of backup and restore on scheduled tasks in persistent schedules, see the Backup and Restore on Scheduled Tasks in Persistent Schedules.
... //Contains the handle to the persistent schedule TInt aScheduleId; ... TInt& aNewId; //Create the task that you want to add the persistent schedule TTaskInfo taskInfo; taskInfo.iTaskId = aNewId; _LIT(aName, "Task for Persistent Schedule"); taskInfo.iName = aName; taskInfo.iPriority = 2; taskInfo.iRepeat = 0; HBufC* taskdata = _L("the data").AllocLC(); iScheduler.ScheduleTask(taskInfo, *taskdata, aScheduleId); //Update aNewId with the task ID set by the task scheduler aNewId = taskInfo.iTaskId; ... CleanupStack::PopAndDestroy(); // taskdata ...Notes:
The HBufC* taskdata
parameter is used by clients who
want to send data to the executable that is launched when the task becomes
due. When the executable is launched, this data is stored in a temporary task
file and the filename is passed on the command line to the newly created process.
That executable can then open the file and stream in the contents.
If multiple tasks are assigned to a schedule that has become due, the
data for each schedule is concatenated into the same file. The tasks are stored
in the file as CScheduledTask
instances. The first item
in the file is an integer describing how many tasks there are in the file.
Subsequently the file just contains tasks which can be streamed in using the CScheduledTask::NewLC()
method.
//Array that holds schedule entries CArrayFixFlat<TSchedulerItemRef>* CSchItemRefArray; CSchItemRefArray = new CArrayFixFlat<TSchedulerItemRef>(3); CleanupStack::PushL(CSchItemRefArray); //Get the list of all schedules User::LeaveIfError(iScheduler.GetScheduleRefsL(*CSchItemRefArray, EAllSchedules)); ... //Gets the schedule handle and assigns it to schedHandle TInt schedHandle = *CSchItemRefArray)[1].iHandle; ...
Viewing details of time-based schedules:
... CArrayFixFlat<TTaskInfo> CTaskInfoArray; CTaskInfoArray* tasks = new (ELeave) CTaskInfoArray(3); TTsTime nextTimeScheduleIsDue; TScheduleState2 stateTimebasedSched; CArrayFixFlat<TScheduleEntryInfo2> CScheduleEntryInfoArray; CScheduleEntryInfoArray* entries = new (ELeave) CScheduleEntryInfoArray(3); CleanupStack::PushL(entries); iScheduler.GetScheduleL(schedHandle, stateTimebasedSched, *entries, tasks, nextTimeScheduleIsDue); CleanupStack::PopAndDestroy(entries);
Viewing details of condition-based schedules:
... TTsTime defaultTime; TScheduleState2 state; CArrayFixFlat<TTaskInfo> CTaskInfoArray; CTaskInfoArray* tasks = new (ELeave) CTaskInfoArray(3); CArrayFixFlat<TTaskSchedulerCondition> CSchConditionArray; CSchConditionArray* conditionList = new (ELeave) CSchConditionArray(3); CleanupStack::PushL(conditionList); iScheduler.GetScheduleL(schedHandle, state, *conditionList, defaultTime, tasks); CleanupStack::PopAndDestroy(conditionList);
Viewing the schedule type associated with a schedule: Identifies whether the schedule is a condition or time-based.
... TScheduleType &type; iScheduler.GetScheduleTypeL(schedHandle, type);
//Editing time-based schedules ... TInt schedHandle; ... //Disables the schedule referenced by "schedHandle" User::LeaveIfError(iScheduler.DisableSchedule(schedHandle); ... //Array to hold the schedule entries CArrayFixFlat<TScheduleEntryInfo2> CSchEntryInfoArray; CSchEntryInfoArray* entryList = new (ELeave) CSchEntryInfoArray(3); CleanupStack::PushL(entryList); //Change the start date and time as Jan 10th, 2010, 11:00 am TDateTime datetime2(2010, EJanuary, 10, 11, 0, 0, 0); TTsTime defaultRuntime(datetime2, ETrue); //create the schedule entry with the updated time TScheduleEntryInfo2 entry1 (defaultRuntime, EDaily, 1, 20); // 20m from "now" entryList->AppendL(entry1); //Enables the schedule referenced by "schedHandle" User::LeaveIfError(iScheduler.EnableSchedule(schedHandle); //edit the schedule User::LeaveIfError(iScheduler.EditSchedule(schedHandle, entryList)); CleanupStack::PopAndDestroy(entryList);The following code snippet illustrates how to edit a condition-based schedule by passing the schedule handle of the schedule to be edited and the updated schedule condition details to RScheduler::EditSchedule().
//Editing condition-based schedules ... TInt schedHandle; ... CArrayFixFlat<TTaskSchedulerCondition>* CSchConditionArray; CSchConditionArray conditionList = new (ELeave) CSchConditionArray(2); CleanupStack::PushL(conditionList); //update the condition TTaskSchedulerCondition condition1; //UID of the publish and subscribe category for condition1 const TUid KPubSubsTransCondCategUid1 = TUid::Uid(0x102F7785); //Key of the publish and subscribe category for condition1 const TInt KPubSubsTransCondKey1 = 1; condition1.iCategory = KPubSubsTransCondCategUid1; condition1.iKey = KPubSubsTransCondKey1; condition1.iState = 10; condition1.iType = TTaskSchedulerCondition::EEquals; conditionList->AppendL(condition1); // sets the date and time as Jan 10th, 2010, 10:00 am TDateTime datetime2(2010, EJanuary, 10, 10, 0, 0, 0); TTsTime defaultRuntime(datetime2, ETrue); iScheduler.EditSchedule(schedHandle, *conditionList, defaultRuntime); ...
... //Deletes the schedule referenced by "schedHandle" iScheduler.DeleteSchedule(schedHandle);
//Array to hold the list of tasks CArrayFixFlat<TSchedulerItemRef> CSchItemRefArray; CSchItemRefArray* refs = new (ELeave) CSchItemRefArray(3); //Gets the list of tasks iScheduler.GetTaskRefsL(*refs, EAllSchedules, EAllTasks); CleanupStack::PopAndDestroy(refs);
... //Handle to the task TInt aTaskHandle; ... TInt taskSize = 0; //Gets the size of the data to be passed to the task's program. taskSize = iScheduler.GetTaskDataSize(aTaskHandle, taskSize); HBufC* taskData = HBufC::NewLC(taskSize); TPtr pTaskData = taskData->Des(); TTsime scheduleNextDueTime; TTaskInfo taskFromServer; TSchedulerItemRef scheduleReference; //Gets task details iScheduler.GetTaskInfoL(aTaskHandle, taskFromServer, pTaskData, scheduleReference, scheduleNextDueTime); CleanupStack::PopAndDestroy(taskData);
TInt taskId; ... iScheduler.DeleteTask(taskId);