Worker thread build error in NS 3.0


#1

Migrating my app from NS 2.5 to NS 3.0

I’ve got worker threads and have:

global.onmessage = function(msg)
{
}

I’m getting an undefined on “onmessage”. I’ve got it defined as described in the docs for NS 2.5 - works.

Also seems like the signature for postMessage() has changed.


#2

We’ve made no changes to the Workers API since they’ve been released. Make sure the scripts where you define global.onmessage on are indeed used as worker scripts. And how do you get undefined on 'onmessage'? A more specific example of your case will help.


#3

I’ve got a separate worker.ts file and the file contents are

require(‘globals’); // necessary to bootstrap tns modules on the new thread

global.onmessage = function(msg)
{
}

The error I get is

error TS2339: Property ‘onmessage’ does not exist on type ‘Global’.

I think the problem has to do with typescript version and conflict on some global definitions (es6, es2016 etc). Because it’s also complaining about the signature of postMessage() method - I think a conflict with another postMessage().

Here’s my post on SO - https://stackoverflow.com/questions/46229156/nativescript-problems-migrating-from-ns-2-to-3

(apologies if that’s a no-no - I can re-edit).


#4

I see that “global” is defined in node_modules\tns-core-modules\modules.d.ts

“onmessage” is not a defined property in the definition of the Global class.

Hence the error.

if I changed my code to

(<any>global).onmessage = …

The error goes away.

But again I think my typescript installation, definitions somewhere is screwed up.

I created a sample template project and was able to run it.

The only difference I saw was my “nativescript-dev-typescript” was updated to 0.3.7 - not 0.5 (in the template project).

But I did do a “tns plugin install nativescript-dev-typescript” - but it installed 0.3.7 only.


#5

To help get to the bottom of this…

I created a template typescript project - build and ran under Android fine.

Then I added the following worker.ts file

require('globals'); // necessary to bootstrap tns modules on the new thread


global.onmessage = function(msg)
{

    postMessage( { } );
}

global.onclose = function()
{
    console.log( "onclose");
}



Got error on onmessage postMessage and onclose.

Where did it go wrong?

app/worker.ts(4,8): error TS2339: Property ‘onmessage’ does not exist on type ‘Global’.
app/worker.ts(7,5): error TS2346: Supplied parameters do not match any signature of call target.
app/worker.ts(10,8): error TS2339: Property ‘onclose’ does not exist on type ‘Global’.


#6

Can I get some help from NS gurus.

I’m following the exact steps in

multithreading-model

Works in NS 2.5 but my code no longer in NS 3.x

I’m pretty sure it has to do with some TS lib file definition or the wrong one being used.


#7

Copy-paste the Worker definitions if you like - https://github.com/NativeScript/NativeScript/blob/1c2ab2adc96eeb122cdb2beea131b84428a9f8ca/tns-core-modules/webworker.es2016.d.ts

I don’t know why they have been removed, but I’d assume it’s because another library defines them already.

Still, if it’s that much of a showstopper - cast global to any and move on.

(<any>global).onmessage = function(msg) { .... }


#8

That still doesn’t take care of postMessage() signature - it seems to be matching another definition.

Also this file webworker.es2016.d.ts is missing in my tns-core-modules.

Looking around I see these lib.xxx.d.ts files are now in /node_modules/typescript/lib folder.

The problem seems to be that in lib.dom.ts file - there are multiple definition of postMessage - and the compiler is picking the wrong one.
The correct one is below

interface Worker extends EventTarget, AbstractWorker {
onmessage: (this: Worker, ev: MessageEvent) => any;
postMessage(message: any, transfer?: any[]): void;
terminate(): void;
addEventListener(type: K, listener: (this: Worker, ev: WorkerEventMap[K]) => any, useCapture?: boolean): void;
addEventListener(type: string, listener: EventListenerOrEventListenerObject, useCapture?: boolean): void;
}

How can I force the compiler to pick the right one?

I don’t think “this” is valid in my code - when the worker thread is being run.

require(‘globals’); // necessary to bootstrap tns modules on the new thread

(global).onmessage = function( ev )
{

postMessage( { } );

};