1# Synchronous Task Development (TaskPool and Worker) 2 3 4Synchronous tasks involve coordinating execution across multiple threads to ensure that tasks run in a specific order and adhere to certain rules, such as using locks to prevent data races. 5 6 7To implement synchronous tasks, you must consider the collaboration and synchronization between multiple threads and ensure data integrity and correct program execution. 8 9TaskPool is well-suited for individual, independent tasks. Therefore, it is recommended for scenarios where synchronous tasks are relatively independent, such as a series of static methods or methods implemented using a singleton pattern. Conversely, if synchronous tasks are interdependent, Worker is the better choice. 10 11 12## Using TaskPool for Independent Synchronous Tasks 13 14TaskPool is recommended in the following scenarios: 15 16- Tasks that are scheduled independently. 17 18- Tasks that are implemented using static methods. 19 20- Singleton handles or class objects used across threads. 21 22> **NOTE** 23> 24> Due to the memory isolation feature of the [actor model](multi-thread-concurrency-overview.md#actor-model) between threads, regular singletons cannot be shared across threads. This issue can be solved by exporting singletons through sendable modules. 25 261. Define a concurrent function to implement service logic. 27 282. Create a [task](../reference/apis-arkts/js-apis-taskpool.md#task), and execute the task using the [execute()](../reference/apis-arkts/js-apis-taskpool.md#taskpoolexecute-1) interface. 29 303. Perform operations on the task result. 31 32In the following example, the service logic uses TaskPool to call related synchronous methods. First, define the concurrent function **taskpoolFunc**, which must be decorated with [@Concurrent](taskpool-introduction.md#concurrent-decorator). Then, define the function **mainFunc**, which creates tasks, executes them, and processes the results returned by the tasks. 33 34 35```ts 36// Index.ets code 37import { taskpool} from '@kit.ArkTS'; 38 39// Step 1: Define a concurrent function to implement service logic. 40@Concurrent 41async function taskpoolFunc(num: number): Promise<number> { 42 // Implement the corresponding functionality based on the service logic. 43 let tmpNum: number = num + 100; 44 return tmpNum; 45} 46 47async function mainFunc(): Promise<void> { 48 // Step 2: Create and execute a task. 49 let task1: taskpool.Task = new taskpool.Task(taskpoolFunc, 1); 50 let res1: number = await taskpool.execute(task1) as number; 51 let task2: taskpool.Task = new taskpool.Task(taskpoolFunc, res1); 52 let res2: number = await taskpool.execute(task2) as number; 53 // Step 3: Perform operations on the result returned by the task. 54 console.info("taskpool: task res1 is: " + res1); 55 console.info("taskpool: task res2 is: " + res2); 56} 57 58@Entry 59@Component 60struct Index { 61 @State message: string = 'Hello World'; 62 63 build() { 64 Row() { 65 Column() { 66 Text(this.message) 67 .fontSize(50) 68 .fontWeight(FontWeight.Bold) 69 .onClick(async () => { 70 mainFunc(); 71 }) 72 } 73 .width('100%') 74 .height('100%') 75 } 76 } 77} 78``` 79<!-- @[taskpool_handle_sync_task](https://gitee.com/openharmony/applications_app_samples/blob/master/code/DocsSample/ArkTS/ArkTsConcurrent/ApplicationMultithreadingDevelopment/ApplicationMultithreading/entry/src/main/ets/managers/SyncTaskDevelopment.ets) --> 80 81 82## Using Worker for Interdependent Synchronous Tasks 83 84When a series of synchronous tasks needs to be scheduled using the same handle, or when they depend on a specific class object that cannot be shared across different task pools, Worker is the appropriate choice. 85 861. Create a Worker object in the UI main thread and receive messages from the Worker thread. DevEco Studio supports generation of Worker templates with a single click. In the corresponding {moduleName} directory, right-click anywhere and choose **New > Worker** to automatically generate the Worker template files and configuration information. 87 88 ```ts 89 // Index.ets 90 import { worker } from '@kit.ArkTS'; 91 92 @Entry 93 @Component 94 struct Index { 95 @State message: string = 'Hello World'; 96 97 build() { 98 Row() { 99 Column() { 100 Text(this.message) 101 .fontSize(50) 102 .fontWeight(FontWeight.Bold) 103 .onClick(() => { 104 let w: worker.ThreadWorker = new worker.ThreadWorker('entry/ets/workers/MyWorker.ts'); 105 w.onmessage = (): void => { 106 // Receive results from the Worker thread. 107 } 108 w.onAllErrors = (): void => { 109 // Receive error messages from the Worker thread. 110 } 111 // Send a Set message to the Worker thread. 112 w.postMessage({'type': 0, 'data': 'data'}) 113 // Send a Get message to the Worker thread. 114 w.postMessage({'type': 1}) 115 // ... 116 // Destroy the thread based on actual service requirements. 117 w.terminate() 118 }) 119 } 120 .width('100%') 121 } 122 .height('100%') 123 } 124 } 125 ``` 126 <!-- @[worker_handle_associated_sync_task](https://gitee.com/openharmony/applications_app_samples/blob/master/code/DocsSample/ArkTS/ArkTsConcurrent/ApplicationMultithreadingDevelopment/ApplicationMultithreading/entry/src/main/ets/managers/SyncTaskDevelopment.ets) --> 127 128 1292. Bind the Worker object in the Worker thread and process the synchronous task logic. 130 131 ```ts 132 // handle.ts code 133 export default class Handle { 134 syncGet() { 135 return; 136 } 137 138 syncSet(num: number) { 139 return; 140 } 141 } 142 ``` 143 <!-- @[worker_handle_associated_sync_task](https://gitee.com/openharmony/applications_app_samples/blob/master/code/DocsSample/ArkTS/ArkTsConcurrent/ApplicationMultithreadingDevelopment/ApplicationMultithreading/entry/src/main/ets/workers/handle.ts) --> 144 145 ```ts 146 // MyWorker.ts code 147 import { worker, ThreadWorkerGlobalScope, MessageEvents } from '@kit.ArkTS'; 148 import Handle from './handle' // Import the handle. 149 150 let workerPort : ThreadWorkerGlobalScope = worker.workerPort; 151 152 // Handle that cannot be transferred. All operations depend on this handle. 153 let handler: Handle = new Handle() 154 155 // onmessage() logic of the Worker thread. 156 workerPort.onmessage = (e : MessageEvents): void => { 157 switch (e.data.type as number) { 158 case 0: 159 handler.syncSet(e.data.data); 160 workerPort.postMessage('success set'); 161 break; 162 case 1: 163 handler.syncGet(); 164 workerPort.postMessage('success get'); 165 break; 166 } 167 } 168 ``` 169 <!-- @[worker_handle_associated_sync_task](https://gitee.com/openharmony/applications_app_samples/blob/master/code/DocsSample/ArkTS/ArkTsConcurrent/ApplicationMultithreadingDevelopment/ApplicationMultithreading/entry/src/main/ets/workers/MyWorker2.ts) --> 170