1 | "use strict";
|
2 | var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
3 | return new (P || (P = Promise))(function (resolve, reject) {
|
4 | function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
5 | function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
6 | function step(result) { result.done ? resolve(result.value) : new P(function (resolve) { resolve(result.value); }).then(fulfilled, rejected); }
|
7 | step((generator = generator.apply(thisArg, _arguments || [])).next());
|
8 | });
|
9 | };
|
10 | var __importDefault = (this && this.__importDefault) || function (mod) {
|
11 | return (mod && mod.__esModule) ? mod : { "default": mod };
|
12 | };
|
13 | Object.defineProperty(exports, "__esModule", { value: true });
|
14 | const function_handle_registry_1 = __importDefault(require("./function-handle-registry"));
|
15 | const command_coordinator_1 = __importDefault(require("./command-coordinator"));
|
16 | class Stagehand {
|
17 | constructor(implementation) {
|
18 | this.rehydrateRemoteFunction = (handleID) => {
|
19 | return (...params) => {
|
20 | if (!this.commandCoordinator) {
|
21 | throw new Error('Cannot call function through a disconnected stagehand');
|
22 | }
|
23 | return this.commandCoordinator.sendCommand('call', handleID, params);
|
24 | };
|
25 | };
|
26 | this.executor = {
|
27 | call: (name, args) => {
|
28 | let thisValue;
|
29 | let fun;
|
30 | if (typeof name === 'string') {
|
31 | fun = this.implementation && this.implementation[name];
|
32 | thisValue = this.implementation;
|
33 | }
|
34 | else {
|
35 | fun = this.handleRegistry.lookupFunction(name);
|
36 | thisValue = null;
|
37 | }
|
38 | if (typeof fun !== 'function') {
|
39 | throw new Error('Unable to call a nonexistent or non-function field ');
|
40 | }
|
41 | return fun.apply(thisValue, args);
|
42 | },
|
43 | handshake: () => {
|
44 | if (!this.implementation) {
|
45 | return { name: 'void', methods: [] };
|
46 | }
|
47 | let name = this.implementation.constructor.name;
|
48 | let methods = [];
|
49 | let object = this.implementation;
|
50 | while (object && object !== Object.prototype) {
|
51 | for (let key of Object.getOwnPropertyNames(object)) {
|
52 | if (typeof this.implementation[key] === 'function' && key !== 'constructor') {
|
53 | methods.push(key);
|
54 | }
|
55 | }
|
56 | object = Object.getPrototypeOf(object);
|
57 | }
|
58 | return { name, methods };
|
59 | },
|
60 | disconnect: () => {
|
61 | setTimeout(() => this.shutdown());
|
62 | }
|
63 | };
|
64 | this.implementation = implementation;
|
65 | this.handleRegistry = new function_handle_registry_1.default(this.rehydrateRemoteFunction);
|
66 | }
|
67 | isConnected() {
|
68 | return !!this.commandCoordinator;
|
69 | }
|
70 | listen(endpoint) {
|
71 | return __awaiter(this, void 0, void 0, function* () {
|
72 | yield this.startup(endpoint);
|
73 | });
|
74 | }
|
75 | connect(endpoint) {
|
76 | return __awaiter(this, void 0, void 0, function* () {
|
77 | yield this.startup(endpoint);
|
78 | return this.commandCoordinator.sendCommand('handshake');
|
79 | });
|
80 | }
|
81 | call(method, args) {
|
82 | return __awaiter(this, void 0, void 0, function* () {
|
83 | if (!this.commandCoordinator) {
|
84 | throw new Error('Stagehand is disconnected');
|
85 | }
|
86 | return this.commandCoordinator.sendCommand('call', method, args);
|
87 | });
|
88 | }
|
89 | disconnect() {
|
90 | return __awaiter(this, void 0, void 0, function* () {
|
91 | if (this.commandCoordinator) {
|
92 | yield this.commandCoordinator.sendCommand('disconnect');
|
93 | }
|
94 | this.shutdown();
|
95 | });
|
96 | }
|
97 | startup(endpoint) {
|
98 | return __awaiter(this, void 0, void 0, function* () {
|
99 | yield this.disconnect();
|
100 | this.endpoint = endpoint;
|
101 | this.commandCoordinator = new command_coordinator_1.default(endpoint, this.handleRegistry, this.executor);
|
102 | });
|
103 | }
|
104 | shutdown() {
|
105 | this.handleRegistry.reset();
|
106 | this.commandCoordinator = undefined;
|
107 | if (this.endpoint) {
|
108 | this.endpoint.disconnect();
|
109 | }
|
110 | }
|
111 | }
|
112 | exports.default = Stagehand;
|