Skip to content

Commit 797efe7

Browse files
committed
Fix loading within the CLI (coder#27)
* Fix loading within the CLI * Remove app * Remove promise handle * Fix requested changes
1 parent a85af49 commit 797efe7

28 files changed

Lines changed: 477 additions & 105 deletions

packages/logger/src/logger.ts

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -272,8 +272,9 @@ export class Logger {
272272
if (name) {
273273
this.nameColor = hashStringToColor(name);
274274
}
275-
if (process.env.LOG_LEVEL) {
276-
switch (process.env.LOG_LEVEL) {
275+
const envLevel = typeof global !== "undefined" && typeof global.process !== "undefined" ? global.process.env.LOG_LEVEL : process.env.LOG_LEVEL;
276+
if (envLevel) {
277+
switch (envLevel) {
277278
case "debug": this.level = Level.Debug; break;
278279
case "info": this.level = Level.Info; break;
279280
case "warn": this.level = Level.Warn; break;

packages/protocol/package.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,8 @@
44
"dependencies": {
55
"express": "^4.16.4",
66
"google-protobuf": "^3.6.1",
7-
"node-pty": "^0.8.0",
7+
"node-pty": "^0.8.1",
8+
"tslib": "^1.9.3",
89
"ws": "^6.1.2"
910
},
1011
"devDependencies": {

packages/protocol/src/browser/client.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -327,6 +327,7 @@ export class Client {
327327
workingDirectory: init.getWorkingDirectory(),
328328
os: opSys,
329329
shell: init.getShell(),
330+
builtInExtensionsDirectory: init.getBuiltinExtensionsDir(),
330331
};
331332
this.initDataEmitter.emit(this._initData);
332333
} else if (message.hasEvalDone()) {

packages/protocol/src/browser/modules/fs.ts

Lines changed: 32 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ import { Client } from "../client";
88
// Use this to get around Webpack inserting our fills.
99
// TODO: is there a better way?
1010
declare var _require: typeof require;
11+
declare var _Buffer: typeof Buffer;
1112

1213
/**
1314
* Implements the native fs module
@@ -121,7 +122,7 @@ export class FS {
121122
const ae = this.client.run((ae, path, options) => {
122123
const fs = _require("fs") as typeof import("fs");
123124
const str = fs.createWriteStream(path, options);
124-
ae.on("write", (d, e) => str.write(Buffer.from(d, e)));
125+
ae.on("write", (d, e) => str.write(_Buffer.from(d, "utf8")));
125126
ae.on("close", () => str.close());
126127
str.on("close", () => ae.emit("close"));
127128
str.on("open", (fd) => ae.emit("open", fd));
@@ -216,18 +217,18 @@ export class FS {
216217
this.client.evaluate((fd) => {
217218
const fs = _require("fs") as typeof import("fs");
218219
const util = _require("util") as typeof import("util");
220+
const tslib = _require("tslib") as typeof import("tslib");
219221

220222
return util.promisify(fs.fstat)(fd).then((stats) => {
221-
return {
222-
...stats,
223-
_isBlockDevice: stats.isBlockDevice(),
224-
_isCharacterDevice: stats.isCharacterDevice(),
223+
return tslib.__assign(stats, {
224+
_isBlockDevice: stats.isBlockDevice ? stats.isBlockDevice() : false,
225+
_isCharacterDevice: stats.isCharacterDevice ? stats.isCharacterDevice() : false,
225226
_isDirectory: stats.isDirectory(),
226-
_isFIFO: stats.isFIFO(),
227+
_isFIFO: stats.isFIFO ? stats.isFIFO() : false,
227228
_isFile: stats.isFile(),
228-
_isSocket: stats.isSocket(),
229-
_isSymbolicLink: stats.isSymbolicLink(),
230-
};
229+
_isSocket: stats.isSocket ? stats.isSocket() : false,
230+
_isSymbolicLink: stats.isSymbolicLink ? stats.isSymbolicLink() : false,
231+
});
231232
});
232233
}, fd).then((stats) => {
233234
callback(undefined!, new Stats(stats));
@@ -322,18 +323,18 @@ export class FS {
322323
this.client.evaluate((path) => {
323324
const fs = _require("fs") as typeof import("fs");
324325
const util = _require("util") as typeof import("util");
326+
const tslib = _require("tslib") as typeof import("tslib");
325327

326328
return util.promisify(fs.lstat)(path).then((stats) => {
327-
return {
328-
...stats,
329-
_isBlockDevice: stats.isBlockDevice(),
330-
_isCharacterDevice: stats.isCharacterDevice(),
329+
return tslib.__assign(stats, {
330+
_isBlockDevice: stats.isBlockDevice ? stats.isBlockDevice() : false,
331+
_isCharacterDevice: stats.isCharacterDevice ? stats.isCharacterDevice() : false,
331332
_isDirectory: stats.isDirectory(),
332-
_isFIFO: stats.isFIFO(),
333+
_isFIFO: stats.isFIFO ? stats.isFIFO() : false,
333334
_isFile: stats.isFile(),
334-
_isSocket: stats.isSocket(),
335-
_isSymbolicLink: stats.isSymbolicLink(),
336-
};
335+
_isSocket: stats.isSocket ? stats.isSocket() : false,
336+
_isSymbolicLink: stats.isSymbolicLink ? stats.isSymbolicLink() : false,
337+
});
337338
});
338339
}, path).then((stats) => {
339340
callback(undefined!, new Stats(stats));
@@ -397,7 +398,7 @@ export class FS {
397398
this.client.evaluate((fd, length, position) => {
398399
const fs = _require("fs") as typeof import("fs");
399400
const util = _require("util") as typeof import("util");
400-
const buffer = new Buffer(length);
401+
const buffer = new _Buffer(length);
401402

402403
return util.promisify(fs.read)(fd, buffer, 0, length, position).then((resp) => {
403404
return {
@@ -513,18 +514,22 @@ export class FS {
513514
this.client.evaluate((path) => {
514515
const fs = _require("fs") as typeof import("fs");
515516
const util = _require("util") as typeof import("util");
517+
const tslib = _require("tslib") as typeof import("tslib");
516518

517519
return util.promisify(fs.stat)(path).then((stats) => {
518-
return {
519-
...stats,
520-
_isBlockDevice: stats.isBlockDevice(),
521-
_isCharacterDevice: stats.isCharacterDevice(),
520+
return tslib.__assign(stats, {
521+
/**
522+
* We need to check if functions exist because nexe's implemented FS
523+
* lib doesnt implement fs.stats properly
524+
*/
525+
_isBlockDevice: stats.isBlockDevice ? stats.isBlockDevice() : false,
526+
_isCharacterDevice: stats.isCharacterDevice ? stats.isCharacterDevice() : false,
522527
_isDirectory: stats.isDirectory(),
523-
_isFIFO: stats.isFIFO(),
528+
_isFIFO: stats.isFIFO ? stats.isFIFO() : false,
524529
_isFile: stats.isFile(),
525-
_isSocket: stats.isSocket(),
526-
_isSymbolicLink: stats.isSymbolicLink(),
527-
};
530+
_isSocket: stats.isSocket ? stats.isSocket() : false,
531+
_isSymbolicLink: stats.isSymbolicLink ? stats.isSymbolicLink() : false,
532+
});
528533
});
529534
}, path).then((stats) => {
530535
callback(undefined!, new Stats(stats));
@@ -602,7 +607,7 @@ export class FS {
602607
const fs = _require("fs") as typeof import("fs");
603608
const util = _require("util") as typeof import("util");
604609

605-
return util.promisify(fs.write)(fd, Buffer.from(buffer, "utf8"), offset, length, position).then((resp) => {
610+
return util.promisify(fs.write)(fd, _Buffer.from(buffer, "utf8"), offset, length, position).then((resp) => {
606611
return {
607612
bytesWritten: resp.bytesWritten,
608613
content: resp.buffer.toString("utf8"),

packages/protocol/src/common/connection.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ export interface InitData {
2121
readonly homeDirectory: string;
2222
readonly tmpDirectory: string;
2323
readonly shell: string;
24+
readonly builtInExtensionsDirectory: string;
2425
}
2526

2627
export interface ISharedProcessData {

packages/protocol/src/node/command.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
11
import * as cp from "child_process";
22
import * as net from "net";
3-
import * as nodePty from "node-pty";
43
import * as stream from "stream";
54
import { TextEncoder } from "text-encoding";
65
import { Logger, logger, field } from "@coder/logger";
@@ -44,6 +43,7 @@ export const handleNewSession = (connection: SendableConnection, newSession: New
4443
});
4544
if (newSession.getTtyDimensions()) {
4645
// Spawn with node-pty
46+
const nodePty = require("node-pty") as typeof import("node-pty");
4747
const ptyProc = nodePty.spawn(newSession.getCommand(), newSession.getArgsList(), {
4848
cols: newSession.getTtyDimensions()!.getWidth(),
4949
rows: newSession.getTtyDimensions()!.getHeight(),
@@ -56,7 +56,7 @@ export const handleNewSession = (connection: SendableConnection, newSession: New
5656
processTitle = ptyProc.process;
5757
const id = new IdentifySessionMessage();
5858
id.setId(newSession.getId());
59-
id.setTitle(processTitle);
59+
id.setTitle(processTitle!);
6060
const sm = new ServerMessage();
6161
sm.setIdentifySession(id);
6262
connection.send(sm.serializeBinary());

packages/protocol/src/node/evaluate.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -76,7 +76,7 @@ export const evaluate = (connection: SendableConnection, message: NewEvalMessage
7676
connection.send(serverMsg.serializeBinary());
7777
},
7878
} : undefined,
79-
Buffer,
79+
_Buffer: Buffer,
8080
require: typeof __non_webpack_require__ !== "undefined" ? __non_webpack_require__ : require,
8181
_require: typeof __non_webpack_require__ !== "undefined" ? __non_webpack_require__ : require,
8282
tslib_1: require("tslib"), // TODO: is there a better way to do this?
@@ -98,7 +98,7 @@ export const evaluate = (connection: SendableConnection, message: NewEvalMessage
9898
onDispose();
9999
}
100100
} catch (ex) {
101-
sendErr(EvalFailedMessage.Reason.EXCEPTION, ex.toString());
101+
sendErr(EvalFailedMessage.Reason.EXCEPTION, ex.toString() + " " + ex.stack);
102102
}
103103

104104
return eventEmitter ? {

packages/protocol/src/node/server.ts

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ import * as net from "net";
1414
export interface ServerOptions {
1515
readonly workingDirectory: string;
1616
readonly dataDirectory: string;
17+
readonly builtInExtensionsDirectory: string;
1718

1819
forkProvider?(message: NewSessionMessage): cp.ChildProcess;
1920
}
@@ -35,7 +36,10 @@ export class Server {
3536
try {
3637
this.handleMessage(ClientMessage.deserializeBinary(data));
3738
} catch (ex) {
38-
logger.error("Failed to handle client message", field("length", data.byteLength), field("exception", ex));
39+
logger.error("Failed to handle client message", field("length", data.byteLength), field("exception", {
40+
message: ex.message,
41+
stack: ex.stack,
42+
}));
3943
}
4044
});
4145
connection.onClose(() => {
@@ -80,6 +84,7 @@ export class Server {
8084
const initMsg = new WorkingInitMessage();
8185
initMsg.setDataDirectory(options.dataDirectory);
8286
initMsg.setWorkingDirectory(options.workingDirectory);
87+
initMsg.setBuiltinExtensionsDir(options.builtInExtensionsDirectory);
8388
initMsg.setHomeDirectory(os.homedir());
8489
initMsg.setTmpDirectory(os.tmpdir());
8590
const platform = os.platform();
@@ -98,8 +103,8 @@ export class Server {
98103
throw new Error(`unrecognized platform "${platform}"`);
99104
}
100105
initMsg.setOperatingSystem(operatingSystem);
101-
if (process.env.SHELL) {
102-
initMsg.setShell(process.env.SHELL);
106+
if (global.process.env.SHELL) {
107+
initMsg.setShell(global.process.env.SHELL);
103108
}
104109
const srvMsg = new ServerMessage();
105110
srvMsg.setInit(initMsg);

packages/protocol/src/proto/client.proto

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -63,4 +63,5 @@ message WorkingInitMessage {
6363
}
6464
OperatingSystem operating_system = 5;
6565
string shell = 6;
66+
string builtin_extensions_dir = 7;
6667
}

packages/protocol/src/proto/client_pb.d.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -270,6 +270,9 @@ export class WorkingInitMessage extends jspb.Message {
270270
getShell(): string;
271271
setShell(value: string): void;
272272

273+
getBuiltinExtensionsDir(): string;
274+
setBuiltinExtensionsDir(value: string): void;
275+
273276
serializeBinary(): Uint8Array;
274277
toObject(includeInstance?: boolean): WorkingInitMessage.AsObject;
275278
static toObject(includeInstance: boolean, msg: WorkingInitMessage): WorkingInitMessage.AsObject;
@@ -288,6 +291,7 @@ export namespace WorkingInitMessage {
288291
workingDirectory: string,
289292
operatingSystem: WorkingInitMessage.OperatingSystem,
290293
shell: string,
294+
builtinExtensionsDir: string,
291295
}
292296

293297
export enum OperatingSystem {

0 commit comments

Comments
 (0)