在Aurelia和TypeScript

时间:2017-09-05 13:53:23

标签: typescript browserify aurelia web-worker

可悲的是,我无法在整个网络上找到答案。

我有一个基于TypeScript / Aurelia CLI / RequireJS的Aurelia应用。 有这样的结构:

|data
   |-MyService.ts
|workers
   |-SomeWorker.ts/js

存在一个名为aurelia-pal-worker的包,但没有文档或复杂的示例。

到目前为止我尝试了什么

  • Typed-Web-Workers这很好,但限制太多
  • 拥有SomeWorker .js ,并在 aurelia_project 中使用Browserify作为额外的构建步骤。

只要我需要RxJs之类的外部库,Browserify方法就可以工作。 当然,当我尝试require("../data/MyService.ts")时,这会中断。为了实现这一点,我需要将整个构建管道替换为另一个,使用tsify插件通过Browserify运行整个aurelia项目。

在我看来,我有3个选择:

  • 找到一个工作示例,将TypeScript文件编译为Web worker,并使用aurelia-pal-worker导入依赖项。
  • 使用TypedWorker,只需将昂贵的功能投入到以下话题中:
    new TypedWoker(expensiveFuncFromService, handleOutput)
  • 编译MyService.ts以分隔JS文件(而不是捆绑它)并要求它如下:
    require("/scripts/MyService.js")

最后两个似乎对我很有吸引力,但应该很容易做到。任何提示或示例都非常感谢!

PS:对于不熟悉Aurelia的人:它在引擎盖下使用了gulp管道。

1 个答案:

答案 0 :(得分:0)

所以经过一些摆弄后,我换了webpack based solution,这让我可以使用惊人的webpack-worker-loader

这是修改现有项目并快速恢复并再次运行之间的最佳权衡。

这就是它最终的样子:

<强> custom_typings/worker-loader.d.ts

declare module "worker-loader!*" {
  const content: new () => any;
  export = content;
}

<强> worker/some-service.ts

export class SomeService {
  public doStuff() {
    console.log("[SomeService] Stuff was done");
  }
}

<强> worker/my-worker.ts

import "rxjs/add/observable/interval";

import { Observable } from "rxjs/Observable";
import { SomeService } from "./some-service";

const svc = new SomeService();
svc.doStuff();

console.log("[Worker] Did stuff");
onmessage = event => {
    console.log(event);
};

Observable.interval(1000).subscribe(x => postMessage(x));

工人加载后如下:

import * as MyWorker from "worker-loader!./worker/my-worker";
const worker = new MyWorker();
worker.onmessage = msg => console.log("[MyClass] got msg from worker", msg);

它将生成以下控制台输出:

1: "[SomeService] Stuff was done"
2: "[Worker] Did stuff"
3: "[MyClass] got msg from worker", 1
4: "[MyClass] got msg from worker", 2
...

您需要在工作人员中进行全面的DI?

this answer的帮助下,我不知道如何用基于webpack的解决方案重写这一点:

let container: Container = null;
let myService: SuperComplexService = null;

// Import the loader abstraction, so the DI container knows how to resolve our modules.
import("aurelia-pal-worker")
  .then(pal => pal.initialize())
  // We need some polyfills (like "Reflect.defineMetadata")
  .then(() => import("aurelia-polyfills"))
  // Then we get the DI service and create a container
  .then(() => import("aurelia-dependency-injection"))
  .then(({ Container }) => (container = new Container()))
  .then(() => import("../services/my-super-complex-service")) // Here we go!
  .then(({ SuperComplexService }) => (myService = container.get(SuperComplexService) as SuperComplexService))
  .then(() => startWorker());

const startWorker = async() => {
  // Let's get going!
}

此装载链的所有积分均转至@ jeremy-danyow。