feat: GameEngineWorker
This commit is contained in:
@@ -45,18 +45,15 @@ class GameEngineController {
|
|||||||
|
|
||||||
const { port1: rpcServer, port2: rpcClient } = new MessageChannel();
|
const { port1: rpcServer, port2: rpcClient } = new MessageChannel();
|
||||||
|
|
||||||
const worker = new Worker(workerPath, {
|
const worker = new Worker(workerPath);
|
||||||
workerData: {
|
|
||||||
guid
|
|
||||||
}
|
|
||||||
});
|
|
||||||
this.stopWaiter = new Promise((resolve) => {
|
this.stopWaiter = new Promise((resolve) => {
|
||||||
this.stopWaiterResolve = resolve;
|
this.stopWaiterResolve = resolve;
|
||||||
});
|
});
|
||||||
|
|
||||||
worker.postMessage({
|
worker.postMessage({
|
||||||
type: 'init',
|
type: 'init',
|
||||||
port: rpcServer
|
port: rpcServer,
|
||||||
|
guid
|
||||||
}, [rpcServer]);
|
}, [rpcServer]);
|
||||||
|
|
||||||
await delay(0);
|
await delay(0);
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
import type { RPCLists } from "@sammo/server_util";
|
import type { RPCLists } from "@sammo/server_util";
|
||||||
import type { ActionRequest, ActionResult } from "./GameEngine.js";
|
import type { ActionRequest, ActionResult } from "./GameEngine.js";
|
||||||
|
import type { MessagePort } from "node:worker_threads";
|
||||||
|
|
||||||
|
|
||||||
export type GameEngineRPCDefs = {
|
export type GameEngineRPCDefs = {
|
||||||
@@ -15,4 +15,13 @@ type WorkerUpdate = {
|
|||||||
lastExecuted: string,
|
lastExecuted: string,
|
||||||
}
|
}
|
||||||
|
|
||||||
export type GameEngineMsg = WorkerUpdate;
|
export type GameEngineMsg = WorkerUpdate;
|
||||||
|
|
||||||
|
|
||||||
|
type WorkerInit = {
|
||||||
|
type: 'init',
|
||||||
|
port: MessagePort,
|
||||||
|
guid: string,
|
||||||
|
}
|
||||||
|
|
||||||
|
export type GameEngineWorkerMsg = WorkerInit;
|
||||||
@@ -0,0 +1,48 @@
|
|||||||
|
import { parentPort as _parentPort } from "node:worker_threads";
|
||||||
|
import { type MessagePort } from "node:worker_threads";
|
||||||
|
import type { GameEngineMsg, GameEngineRPCDefs, GameEngineWorkerMsg } from "./GameEngineDefs.js";
|
||||||
|
import { GameEngine } from "./GameEngine.js";
|
||||||
|
import { RPCServer } from "@sammo/server_util";
|
||||||
|
|
||||||
|
if (!_parentPort) {
|
||||||
|
throw new Error('GameEngineWorker must be run as worker');
|
||||||
|
}
|
||||||
|
|
||||||
|
const parentPort = _parentPort;
|
||||||
|
|
||||||
|
function sendToParent(msg: GameEngineMsg) {
|
||||||
|
parentPort.postMessage(msg);
|
||||||
|
}
|
||||||
|
|
||||||
|
let engineDone: () => void = () => { throw new Error('GameEngineWorker: engineDone not set')};
|
||||||
|
let engine: GameEngine;
|
||||||
|
let rpcServer: RPCServer<GameEngineRPCDefs>;
|
||||||
|
|
||||||
|
async function startWorker(port: MessagePort, guid: string){
|
||||||
|
engine = await GameEngine.initInstance(sendToParent);
|
||||||
|
rpcServer = new RPCServer<GameEngineRPCDefs>(port, {
|
||||||
|
stop: async ()=>{
|
||||||
|
await engine.stop();
|
||||||
|
engineDone();
|
||||||
|
},
|
||||||
|
pushAPIAction: async (action)=>{
|
||||||
|
return await engine.pushAPIAction(action);
|
||||||
|
},
|
||||||
|
pushServerAction: async (action)=>{
|
||||||
|
return await engine.pushServerAction(action);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
await new Promise<void>((resolve) => {
|
||||||
|
parentPort.on('message', (msg: GameEngineWorkerMsg) => {
|
||||||
|
switch (msg.type) {
|
||||||
|
case 'init':
|
||||||
|
engineDone = resolve;
|
||||||
|
startWorker(msg.port, msg.guid);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
throw new Error(`GameEngineWorker: unknown message type ${msg.type}`);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
})
|
||||||
Reference in New Issue
Block a user