2021-07-10 19:28:02 +00:00
|
|
|
"use strict";
|
|
|
|
|
2020-07-30 19:43:55 +00:00
|
|
|
// preload.js for Electron app
|
|
|
|
const { ipcRenderer } = require('electron');
|
2020-08-02 04:06:18 +00:00
|
|
|
const fs = require('fs');
|
2021-07-10 19:28:02 +00:00
|
|
|
const _path = require('path');
|
|
|
|
const chokidar = require('chokidar');
|
|
|
|
|
|
|
|
const homeDirectory = require('os').homedir();
|
2021-07-13 16:34:47 +00:00
|
|
|
const wsroot = process.env.HOME_8BITWORKSHOP || _path.join(homeDirectory, '8bitworkshop');
|
2021-07-10 19:28:02 +00:00
|
|
|
|
|
|
|
function getLocalDir() {
|
|
|
|
const _ui = window.ui_1 || window.ui || window; // TODO: module naming
|
|
|
|
var dir = _ui.repo_id || _ui.platform_id || 'default';
|
|
|
|
return _path.join(wsroot, dir);
|
|
|
|
}
|
|
|
|
function getLocalFilePath(path) {
|
|
|
|
return _path.join(getLocalDir(), path);
|
|
|
|
}
|
2020-08-02 04:06:18 +00:00
|
|
|
|
2020-08-31 14:26:37 +00:00
|
|
|
function isProbablyBinary(path, data) {
|
|
|
|
var score = 0;
|
|
|
|
// decode as UTF-8
|
|
|
|
for (var i = 0; i < (data?data.length:0);) {
|
|
|
|
let c = data[i++];
|
|
|
|
if ((c & 0x80) == 0) {
|
|
|
|
// more likely binary if we see a NUL or obscure control character
|
|
|
|
if (c < 9 || (c >= 14 && c < 26) || c == 0x7f) {
|
|
|
|
score++;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
// look for invalid unicode sequences
|
|
|
|
var nextra = 0;
|
|
|
|
if ((c & 0xe0) == 0xc0) nextra = 1;
|
|
|
|
else if ((c & 0xf0) == 0xe0) nextra = 2;
|
|
|
|
else if ((c & 0xf8) == 0xf0) nextra = 3;
|
|
|
|
else if (c < 0xa0) score++;
|
|
|
|
else if (c == 0xff) score++;
|
|
|
|
while (nextra--) {
|
|
|
|
if (i >= data.length || (data[i++] & 0xc0) != 0x80) {
|
|
|
|
score++;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return score > 0;
|
|
|
|
}
|
|
|
|
|
2021-07-10 19:28:02 +00:00
|
|
|
// this is before startUI is called
|
2020-07-30 19:43:55 +00:00
|
|
|
process.once('loaded', () => {
|
2021-07-10 19:28:02 +00:00
|
|
|
var watcher;
|
|
|
|
var allfiles = new Set();
|
|
|
|
// get workspace root dir
|
|
|
|
// from browser: read workspace files asynchronously
|
|
|
|
window.alternateLocalFilesystem = {
|
|
|
|
getFileData: (path) => {
|
|
|
|
let fullpath = getLocalFilePath(path);
|
|
|
|
allfiles.add(fullpath);
|
|
|
|
if (!fs.existsSync(fullpath)) {
|
|
|
|
return null;
|
|
|
|
}
|
|
|
|
return new Promise( (resolve, reject) => {
|
|
|
|
fs.readFile(fullpath, (err,buf) => {
|
|
|
|
if (err) {
|
|
|
|
resolve(err);
|
|
|
|
} else {
|
|
|
|
let isBinary = isProbablyBinary(path, buf);
|
|
|
|
let data = isBinary ? buf : buf.toString('utf-8');
|
|
|
|
console.log("getWorkspaceFile", path, isBinary, data.length);
|
|
|
|
resolve(data);
|
|
|
|
}
|
|
|
|
});
|
|
|
|
});
|
|
|
|
},
|
|
|
|
setFileData: (path, data) => {
|
|
|
|
let fullpath = getLocalFilePath(path);
|
|
|
|
allfiles.add(fullpath);
|
|
|
|
let encoding = typeof data === 'string' ? 'utf8' : null;
|
|
|
|
console.log("setWorkspaceFile", fullpath, data.length);
|
|
|
|
return new Promise( (resolve, reject) => {
|
|
|
|
fs.mkdir(_path.dirname(fullpath), {recursive:true}, (err,dirpath) => {
|
|
|
|
fs.writeFile(fullpath, data, {encoding:encoding}, (err) => {
|
|
|
|
if (err) {
|
|
|
|
reject(err);
|
|
|
|
} else {
|
|
|
|
resolve();
|
|
|
|
}
|
|
|
|
});
|
|
|
|
});
|
|
|
|
});
|
2020-08-03 01:22:20 +00:00
|
|
|
}
|
|
|
|
}
|
2021-07-10 19:28:02 +00:00
|
|
|
// watch/unwatch files as browser loses/gains focus
|
|
|
|
window.addEventListener("blur", (e) => {
|
|
|
|
let localdir = getLocalDir();
|
|
|
|
if (!watcher && localdir) {
|
|
|
|
// watch files for changes
|
|
|
|
watcher = chokidar.watch(Array.from(allfiles), {
|
|
|
|
//awaitWriteFinish: {pollInterval:50,stabilityThreshold:300},
|
|
|
|
ignoreInitial: true
|
|
|
|
});
|
|
|
|
watcher.on('all', (event, path) => {
|
|
|
|
path = path.substring(localdir.length + 1); //strip off prefix
|
|
|
|
console.log('WATCH', event, path);
|
|
|
|
// we don't use awaitWriteFinish b/c we might close() the watcher
|
|
|
|
setTimeout(() => {
|
|
|
|
window.reloadWorkspaceFile(path);
|
|
|
|
}, 300);
|
|
|
|
});
|
|
|
|
console.log('watching', getLocalDir());
|
|
|
|
}
|
|
|
|
});
|
|
|
|
window.addEventListener("focus", (e) => {
|
|
|
|
if (watcher) {
|
|
|
|
watcher.close();
|
|
|
|
watcher = null;
|
|
|
|
}
|
|
|
|
console.log('stopped watching');
|
|
|
|
});
|
|
|
|
|
2020-08-02 04:06:18 +00:00
|
|
|
// from electron.js: set workspace root directory
|
2021-07-10 19:28:02 +00:00
|
|
|
/*
|
|
|
|
TODO
|
2020-08-02 04:06:18 +00:00
|
|
|
ipcRenderer.on('setWorkspaceRoot', (event, data) => {
|
|
|
|
wsroot = data.root;
|
2021-07-10 19:28:02 +00:00
|
|
|
var binpath = _path.join(wsroot, 'bin');
|
2020-08-27 01:42:18 +00:00
|
|
|
if (!fs.existsSync(binpath)) fs.mkdirSync(binpath, {});
|
2020-08-02 04:06:18 +00:00
|
|
|
console.log('setWorkspaceRoot', wsroot);
|
2020-07-30 19:43:55 +00:00
|
|
|
});
|
2020-08-02 04:06:18 +00:00
|
|
|
// from electron.js: file changed
|
|
|
|
ipcRenderer.on('fileChanged', (event, data) => {
|
|
|
|
var path = data.path;
|
|
|
|
window.reloadWorkspaceFile(path);
|
2020-07-30 19:43:55 +00:00
|
|
|
});
|
2021-07-10 19:28:02 +00:00
|
|
|
*/
|
|
|
|
console.log('loaded preload', window.alternateLocalFilesystem, window.startUI);
|
2020-07-30 19:43:55 +00:00
|
|
|
});
|