task.ts 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126
  1. /**
  2. * Copyright (c) 2017 mol* contributors, licensed under MIT, See LICENSE file for more info.
  3. *
  4. * @author David Sehnal <david.sehnal@gmail.com>
  5. */
  6. import { Task, Progress, Scheduler, MultistepTask, chunkedSubtask } from 'mol-task'
  7. import { now } from 'mol-util/now';
  8. export async function test1() {
  9. const t = Task.create('test', async () => 1);
  10. const r = await t.run();
  11. console.log(r);
  12. }
  13. function messageTree(root: Progress.Node, prefix = ''): string {
  14. const p = root.progress;
  15. if (!root.children.length) {
  16. if (p.isIndeterminate) return `${prefix}${p.taskName}: ${p.message}`;
  17. return `${prefix}${p.taskName}: [${p.current}/${p.max}] ${p.message}`;
  18. }
  19. const newPrefix = prefix + ' |_ ';
  20. const subTree = root.children.map(c => messageTree(c, newPrefix));
  21. if (p.isIndeterminate) return `${prefix}${p.taskName}: ${p.message}\n${subTree.join('\n')}`;
  22. return `${prefix}${p.taskName}: [${p.current}/${p.max}] ${p.message}\n${subTree.join('\n')}`;
  23. }
  24. function createTask<T>(delayMs: number, r: T): Task<T> {
  25. return Task.create('delayed value ' + r, async ctx => {
  26. ctx.update('Processing delayed... ' + r, true);
  27. await Scheduler.delay(delayMs);
  28. if (ctx.shouldUpdate) await ctx.update({ message: 'hello from delayed... ' });
  29. return r;
  30. }, () => console.log('On abort called ' + r));
  31. }
  32. export function abortAfter(delay: number) {
  33. return Task.create('abort after ' + delay, async ctx => {
  34. await Scheduler.delay(delay);
  35. throw Task.Aborted('test');
  36. // if (ctx.shouldUpdate) await ctx.update({ message: 'hello from delayed... ' });
  37. // return r;
  38. });
  39. }
  40. export function testTree() {
  41. return Task.create('test o', async ctx => {
  42. await Scheduler.delay(250);
  43. if (ctx.shouldUpdate) await ctx.update({ message: 'hi! 1' });
  44. await Scheduler.delay(125);
  45. if (ctx.shouldUpdate) await ctx.update({ message: 'hi! 2' });
  46. await Scheduler.delay(250);
  47. if (ctx.shouldUpdate) await ctx.update('hi! 3');
  48. // ctx.update('Running children...', true);
  49. const c1 = createTask(250, 1).runAsChild(ctx);
  50. const c2 = createTask(500, 2).runAsChild(ctx);
  51. const c3 = createTask(750, 3).runAsChild(ctx);
  52. // await ctx.runChild(abortAfter(350));
  53. const r = await c1 + await c2 + await c3;
  54. if (ctx.shouldUpdate) await ctx.update({ message: 'Almost done...' });
  55. return r + 1;
  56. });
  57. }
  58. export type ChunkedState = { i: number, current: number, total: number }
  59. function processChunk(n: number, state: ChunkedState): number {
  60. const toProcess = Math.min(state.current + n, state.total);
  61. const start = state.current;
  62. for (let i = start; i < toProcess; i++) {
  63. for (let j = 0; j < 1000000; j++) {
  64. state.i += (i * j + 1 + state.i) % 1023;
  65. state.i = state.i % 1000;
  66. }
  67. }
  68. state.current = toProcess;
  69. return toProcess - start;
  70. }
  71. export const ms = MultistepTask('ms-task', ['step 1', 'step 2', 'step 3'], async (p: { i: number }, step, ctx) => {
  72. await step(0);
  73. const child = Task.create('chunked', async ctx => {
  74. const s = await chunkedSubtask(ctx, 25, { i: 0, current: 0, total: 125 }, processChunk, (ctx, s, p) => ctx.update('chunk test ' + p))
  75. return s.i;
  76. });
  77. await child.runAsChild(ctx);
  78. await Scheduler.delay(250);
  79. await step(1);
  80. await chunkedSubtask(ctx, 25, { i: 0, current: 0, total: 80 }, processChunk, (ctx, s, p) => ctx.update('chunk test ' + p))
  81. await Scheduler.delay(250);
  82. await step(2);
  83. await Scheduler.delay(250);
  84. return p.i + 3;
  85. })
  86. export function abortingObserver(p: Progress) {
  87. console.log(messageTree(p.root));
  88. if (now() - p.root.progress.startedTime > 1000) {
  89. p.requestAbort('test');
  90. }
  91. }
  92. export function logP(p: Progress) { console.log(messageTree(p.root)); }
  93. async function test() {
  94. try {
  95. // const r = await Run(testTree(), p => console.log(messageTree(p.root)), 250);
  96. // const r = await Run(testTree(), abortingObserver, 250);
  97. // console.log(r);
  98. const m = await ms({ i: 10 }).run(logP);
  99. console.log(m);
  100. } catch (e) {
  101. console.error(e);
  102. }
  103. }
  104. test();
  105. // testObs();