forked from JohnEarnest/ok
-
Notifications
You must be signed in to change notification settings - Fork 0
/
repl.js
executable file
·108 lines (103 loc) · 3.12 KB
/
repl.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
#!/usr/bin/env node
var ok = require('./oK');
var fs = require('fs');
var os = require('os');
var path = require('path');
var readline = require('readline');
var conv = require('./convert');
// register I/O hooks
function str(x) { // convert a k string or symbol to a js string
var s = conv.tojs(x);
if (typeof s !== 'string') { throw Error('ERROR: type'); }
return s;
}
function read(x) {
var f = str(x);
if (f) {
f = path.resolve(process.cwd(), f);
return conv.tok(fs.statSync(f).isDirectory() ? fs.readdirSync(f) : fs.readFileSync(f, 'utf8').replace(/\r?\n$/, '').split(/\r?\n/));
} else if (rl) {
throw Error('ERROR: cannot read from stdin while in REPL');
} else {
var b = Buffer(128), b0, n = 0;
while (fs.readSync(process.stdin.fd, b, n, 1) && b[n] !== 10) {
n++;
if (n === b.length) { b0 = b; b = Buffer(2 * n); b0.copy(b, 0, 0, n); b0 = null; } // resize buffer when full
}
return conv.tok(b.toString('utf8', 0, n));
}
}
function write(x, y) {
var s = conv.tojs(y);
if (Array.isArray(s)) { s = s.join('\n') + '\n'; }
if (typeof s !== 'string') { throw Error('ERROR: type'); }
var f = str(x);
if (f) {
fs.writeFileSync(path.resolve(process.cwd(), f), s);
} else {
fs.writeSync(process.stdout.fd, s);
}
return y;
}
for (var i = 0; i < 2; i++) { ok.setIO('0:', i, read ); }
for (var i = 2; i < 6; i++) { ok.setIO('0:', i, write); }
for (var i = 0; i < 2; i++) { ok.setIO('5:', i, function(x) { return conv.tok(ok.format(x)); }); }
var env = ok.baseEnv();
// run user prelude file if exists
try {
var preludeFile = os.homedir() + "/.config/okrc.k"
var program = fs.readFileSync(preludeFile, 'utf8');
ok.run(ok.parse(program), env)
} catch (err) {
if (err.code != 'ENOENT') throw err
}
// process filename.k as a command-line arg
if (process.argv.length > 2) {
var program = fs.readFileSync(process.argv[2], 'utf8');
env.put('x', true, conv.tok(process.argv.slice(3)))
process.stdout.write(ok.format(ok.run(ok.parse(program), env)) + '\n');
process.exit(0);
}
// actual REPL
process.stdout.write('oK v' + ok.version + '\n');
var rl = readline.createInterface({
input: process.stdin,
output: process.stdout,
completer: function (line) {
var m = /[a-z][a-z\d]*$/i.exec(line);
var prefix = m ? m[0] : '';
var names = [];
for (var e = env; e; e = e.p) { // iterate over ancestor environments
for (var name in e.d) {
if (name.slice(0, prefix.length) === prefix && names.indexOf(name) < 0) {
names.push(name);
}
}
}
return [names, prefix];
}
});
rl.on('line', function (line) {
if (line === '\\\\') { process.exit(0); }
var showtime = false;
if (line.lastIndexOf("\\t") == 0) {
line = line.slice(2);
showtime = true;
}
try {
if (line.trim()) {
var starttime = new Date().getTime();
var output = ok.format(ok.run(ok.parse(line), env)) + '\n';
if (showtime) {
var endtime = new Date().getTime();
output += "completed in "+(endtime-starttime)+"ms.\n";
}
process.stdout.write(output);
}
} catch (err) {
process.stdout.write(err.message + '\n');
}
rl.prompt();
});
rl.on('close', function () { process.stdout.write('\n'); process.exit(0); });
rl.setPrompt(' '); rl.prompt();