Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add ability to cancel tasks, and update to allow components to work in node #1230

Open
wants to merge 2 commits into
base: develop
Choose a base branch
from

Conversation

dpvc
Copy link
Member

@dpvc dpvc commented Mar 5, 2025

Overview

The main purposes of this PR are to:

  1. Add the ability to cancel worker tasks (and to do so when MathItems are removed from the document math list)
  2. Support using the components in node applications. (The current code only works for direct imports of the MathJax modules. This extends support to using the MathJax components as well.)

It also changes how the worker handles promises. Rather than having the GeneratorPool create promises, the WorkerHandler's Post() command now does that automatically, so every command send to the worker pool has a promise that resolves when that command is complete.

This change also includes the ability to pass data back from the worker to the client via that promise. This allows the worker to send the speech structure data back via the promise rather than a client Attach() command. The client now uses that data to do the attach action itself. This allows the worker to start processing other commands while the client is attaching the speech from the previous one, since the worker will have finished its command when it passes back the speech structure, rather than having to wait fo the client to attach and then finish.

The Details

In the worker pool configuration file, we add the verisons check (so we don't get an error message about missing version information when a node application's LiteIFrame loads the worker pool data via asyncLoad()).

We add the speech component to the a11y/util.jsso that the combined components that include the assisitive tools will include the speech component.

We extend the asyncLoad() definition in the core component to potentially handle loading node packages (we do that in the LiteIFrame by loading the node:module node package). In a node application that has set the require configuration option properly to either the node require or to (file) => import(file), or an equivalent, this will allow loading of core node modules.

The version of SRE in the lab directory now sets up the mathmaps path to work in the lab. (The typo that I had in the SREfeature that you corrected actually allowed it to work before, but now that that has been corrected, it no longer does, but this takes care of that.)

The speech and Braille controls are removed from the semantic-enrich component, since they are not used there, and are already in the speech component, where they are used.

In speech.ts, the GeneratorPool's Speech() function now returns a promise (see below), so we take advantage of that insteach of using a try/catch construction. We also push the promise into the document's renderPromises array so that MathJax.typesetPromise() will wait for it before resolving. That way, the speech will be on the DOM nodes when the typeset promise resolves (as it is in beta.7).

The MathItem's clear() method now cancels its speech task, if there is one.

The MathDocument now gets a done() method that terminates the worker pool.

In GeneratorPool.ts:

  • Since the Post() command of the WorkerHandler now creates promises automatically (see below), we don't need to get our own promises.
  • The promises can return values, so they are Promise<any> not Promise<void>.
  • The Speech() command now saves that promise and returns it (as do nextRules and nextStyle).
  • A new cancel() method cancels any task saved for this MathItem.

In MessageTypes.ts, the PromiseFunctions are no longer needed, and we add some types for the speech structure that will be passed back from the worker.

In WebWorker.ts:

  • The resolve() function can now pass an argument.
  • The Post() method now creates a promise for the task automatically.
  • The Speech() method is moved down to be next to the nextRules and nextStyle methods.
  • A new Cancel() method is added to allow a pending task to be canceled (removed from the task list) and its promise rejected. We might want to make a convention for this so that warnings aren't produced when tasks are canceled explicitly.
  • The methods that post messages to the worker now all return promises.
  • The Speech() command is now an async function that waits for the worker to return the speech structure and then calls Attach() on using that. (The worker no longer calls Attach() itself, but just returns the data, so it can go on to do other tasks while the speech is being attached.)
  • Similarly for nextRules and nextStyle.
  • The Attach() function has been moved out the worker commands and is now just a regular method. It is also broken into three parts (rather than creating functions internally), and setSpecialAttributes() is moved here along with the other separated out setSpeechAttribute() and setSpeechAttributes().
  • The Terminate() method now rejects all the tasks in the list, and before terminating the worker pool.
  • The Stop() method now waits for the termination to complete before removing the iframe.
  • The Finished() method now returns either the result from the worker, or an error message from it.

In speech-worker.ts:

  • We define the structure types (just to be more expressive), and use them in the copyStructure() commands.
  • The event listener is restructured slightly. All the commands now return promises (se below), so we take advantage of that to then() and catch() rather than a try/catch structure. An error state is indicated by an error property of the msg passed to Finished() (see below).
  • We use WorkerFunction and WorkerResult types for more specificity.
  • The feature() command is removed, since SRE is already configured and loaded, so this would have no effect.
  • The setup() command now waits for the setup to take effect (though the command is not used currently).
  • The Finished() now takes a msg parameter that is sent back to the client. The success property is set according to whether there is an error message or not.
  • The Speech() action is simplified a bit, and now returns the speech structure data rather than asking the client to attach. The client gets the structure data from the promise it got when posting the worker command, and does the attach operation itself.

The LiteIFrame element indicates that asyncLoad needs to load a node module so that the asyncLoad from the core component will not use the Package module's loader.

The loader.ts file now allows the Load() function to return the results of the load operations (i.e., the exported values of the packages that were loaded). This allows the LiteIFrame to get the exported values from the speech-workerpool when components are being used in node. The results are stored in new results properties of the Package data (see below).

In package.ts, we now retain the result of loading a package, i.e., its exported values, so that the component loader can return those.

In startup.ts, we fix a typo with the document used for the toMML() function (argh), and create a new MathJax.done() function that is used to terminate the worker pool, if it was started.

In MathDocument.ts:

  • We add the done() method that can be used to clean up anything when the document is no longer needed. (We use it to terminate the worker pool in the speech handler.)
  • The clearMathItemsWithin() now calls each MathItem's clear() method (used to cancel its speech task, if any).

In MathItem.ts, we add the new clear() method, and call it from the removeFromDocument() method, so that if a MathItem is removed, its tasks are canceled.

Finally, in HTMLMathItem.ts, we make sure the super-class removeFromDocument() is called (so the clear() is performed).

@dpvc dpvc requested a review from zorkow March 5, 2025 14:49
@dpvc dpvc added this to the v4.0 milestone Mar 5, 2025
@dpvc
Copy link
Member Author

dpvc commented Mar 5, 2025

To test in the lab, be sure to run

pnpm -s lab:sre

first, and add

loader: {
  paths: {
    sre: './node_modules/mathjax-full/mjs/a11y/sre'
  }
}

to the configuration in lib/v4-lab.js.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

1 participant