|
|
@ -72,48 +72,50 @@ class FileProvider { |
|
|
|
async exists (path) { |
|
|
|
async exists (path) { |
|
|
|
// todo check the type (directory/file) as well #2386
|
|
|
|
// todo check the type (directory/file) as well #2386
|
|
|
|
// currently it is not possible to have a file and folder with same path
|
|
|
|
// currently it is not possible to have a file and folder with same path
|
|
|
|
const ret = this._exists(path) |
|
|
|
const ret = await this._exists(path) |
|
|
|
|
|
|
|
|
|
|
|
return ret |
|
|
|
return ret |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
_exists (path) { |
|
|
|
async _exists (path) { |
|
|
|
path = this.getPathFromUrl(path) || path // ensure we actually use the normalized path from here
|
|
|
|
path = this.getPathFromUrl(path) || path // ensure we actually use the normalized path from here
|
|
|
|
var unprefixedpath = this.removePrefix(path) |
|
|
|
var unprefixedpath = this.removePrefix(path) |
|
|
|
return path === this.type ? true : window.remixFileSystem.existsSync(unprefixedpath) |
|
|
|
console.log(unprefixedpath) |
|
|
|
|
|
|
|
return path === this.type ? true : await window.remixFileSystem.exists(this.addSlash(unprefixedpath)) |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
init (cb) { |
|
|
|
init (cb) { |
|
|
|
cb() |
|
|
|
cb() |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
get (path, cb) { |
|
|
|
async get (path, cb) { |
|
|
|
cb = cb || function () {} |
|
|
|
|
|
|
|
path = this.getPathFromUrl(path) || path // ensure we actually use the normalized path from here
|
|
|
|
path = this.getPathFromUrl(path) || path // ensure we actually use the normalized path from here
|
|
|
|
var unprefixedpath = this.removePrefix(path) |
|
|
|
var unprefixedpath = this.removePrefix(path) |
|
|
|
var exists = window.remixFileSystem.existsSync(unprefixedpath) |
|
|
|
console.log('getting ', unprefixedpath, await window.remixFileSystem.readFile(this.addSlash(unprefixedpath), 'utf8')) |
|
|
|
if (!exists) return cb(null, null) |
|
|
|
try { |
|
|
|
window.remixFileSystem.readFile(unprefixedpath, 'utf8', (err, content) => { |
|
|
|
const content = await window.remixFileSystem.readFile(this.addSlash(unprefixedpath), 'utf8') |
|
|
|
cb(err, content) |
|
|
|
if (cb) cb(null, content) |
|
|
|
}) |
|
|
|
return content |
|
|
|
|
|
|
|
} catch (err) { |
|
|
|
|
|
|
|
if (cb) cb(err, null) |
|
|
|
|
|
|
|
throw new Error(err) |
|
|
|
|
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
set (path, content, cb) { |
|
|
|
async set (path, content, cb) { |
|
|
|
cb = cb || function () {} |
|
|
|
|
|
|
|
var unprefixedpath = this.removePrefix(path) |
|
|
|
var unprefixedpath = this.removePrefix(path) |
|
|
|
var exists = window.remixFileSystem.existsSync(unprefixedpath) |
|
|
|
const exists = await window.remixFileSystem.exists(unprefixedpath) |
|
|
|
if (exists && window.remixFileSystem.readFileSync(unprefixedpath, 'utf8') === content) { |
|
|
|
if (exists && await window.remixFileSystem.readFile(unprefixedpath, 'utf8') === content) { |
|
|
|
cb() |
|
|
|
if (cb) cb() |
|
|
|
return true |
|
|
|
return null |
|
|
|
} |
|
|
|
|
|
|
|
if (!exists && unprefixedpath.indexOf('/') !== -1) { |
|
|
|
|
|
|
|
// the last element is the filename and we should remove it
|
|
|
|
|
|
|
|
this.createDir(path.substr(0, path.lastIndexOf('/'))) |
|
|
|
|
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
await this.createDir(path.substr(0, path.lastIndexOf('/'))) |
|
|
|
|
|
|
|
console.log('set file', path, unprefixedpath) |
|
|
|
try { |
|
|
|
try { |
|
|
|
window.remixFileSystem.writeFileSync(unprefixedpath, content) |
|
|
|
await window.remixFileSystem.writeFile(this.addSlash(unprefixedpath), content, 'utf8') |
|
|
|
} catch (e) { |
|
|
|
} catch (e) { |
|
|
|
cb(e) |
|
|
|
if (cb) cb(e) |
|
|
|
return false |
|
|
|
return false |
|
|
|
} |
|
|
|
} |
|
|
|
if (!exists) { |
|
|
|
if (!exists) { |
|
|
@ -121,22 +123,26 @@ class FileProvider { |
|
|
|
} else { |
|
|
|
} else { |
|
|
|
this.event.emit('fileChanged', this._normalizePath(unprefixedpath)) |
|
|
|
this.event.emit('fileChanged', this._normalizePath(unprefixedpath)) |
|
|
|
} |
|
|
|
} |
|
|
|
cb() |
|
|
|
if (cb) cb() |
|
|
|
return true |
|
|
|
return true |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
createDir (path, cb) { |
|
|
|
async createDir (path, cb) { |
|
|
|
const unprefixedpath = this.removePrefix(path) |
|
|
|
const unprefixedpath = this.removePrefix(path) |
|
|
|
const paths = unprefixedpath.split('/') |
|
|
|
const paths = unprefixedpath.split('/') |
|
|
|
if (paths.length && paths[0] === '') paths.shift() |
|
|
|
if (paths.length && paths[0] === '') paths.shift() |
|
|
|
let currentCheck = '' |
|
|
|
let currentCheck = '' |
|
|
|
paths.forEach((value) => { |
|
|
|
for (const value of paths) { |
|
|
|
currentCheck = currentCheck + '/' + value |
|
|
|
currentCheck = currentCheck + '/' + value |
|
|
|
if (!window.remixFileSystem.existsSync(currentCheck)) { |
|
|
|
if (!await window.remixFileSystem.exists(currentCheck)) { |
|
|
|
window.remixFileSystem.mkdirSync(currentCheck) |
|
|
|
try { |
|
|
|
this.event.emit('folderAdded', this._normalizePath(currentCheck)) |
|
|
|
await window.remixFileSystem.mkdir(currentCheck) |
|
|
|
|
|
|
|
this.event.emit('folderAdded', this._normalizePath(currentCheck)) |
|
|
|
|
|
|
|
} catch (error) { |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
}) |
|
|
|
} |
|
|
|
if (cb) cb() |
|
|
|
if (cb) cb() |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
@ -150,55 +156,51 @@ class FileProvider { |
|
|
|
return false |
|
|
|
return false |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
isDirectory (path) { |
|
|
|
async isDirectory (path) { |
|
|
|
const unprefixedpath = this.removePrefix(path) |
|
|
|
const unprefixedpath = this.removePrefix(path) |
|
|
|
|
|
|
|
return path === this.type ? true : (await window.remixFileSystem.stat(this.addSlash(unprefixedpath))).isDirectory() |
|
|
|
return path === this.type ? true : window.remixFileSystem.statSync(unprefixedpath).isDirectory() |
|
|
|
|
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
isFile (path) { |
|
|
|
async isFile (path) { |
|
|
|
path = this.getPathFromUrl(path) || path // ensure we actually use the normalized path from here
|
|
|
|
path = this.getPathFromUrl(path) || path // ensure we actually use the normalized path from here
|
|
|
|
path = this.removePrefix(path) |
|
|
|
path = this.removePrefix(path) |
|
|
|
return window.remixFileSystem.statSync(path).isFile() |
|
|
|
return (await window.remixFileSystem.stat(this.addSlash(path))).isFile() |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
/** |
|
|
|
/** |
|
|
|
* Removes the folder recursively |
|
|
|
* Removes the folder recursively |
|
|
|
* @param {*} path is the folder to be removed |
|
|
|
* @param {*} path is the folder to be removed |
|
|
|
*/ |
|
|
|
*/ |
|
|
|
remove (path) { |
|
|
|
async remove (path) { |
|
|
|
return new Promise((resolve, reject) => { |
|
|
|
path = this.removePrefix(path) |
|
|
|
path = this.removePrefix(path) |
|
|
|
if (await window.remixFileSystem.exists(path)) { |
|
|
|
if (window.remixFileSystem.existsSync(path)) { |
|
|
|
const stat = await window.remixFileSystem.stat(path) |
|
|
|
const stat = window.remixFileSystem.statSync(path) |
|
|
|
try { |
|
|
|
try { |
|
|
|
if (!stat.isDirectory()) { |
|
|
|
if (!stat.isDirectory()) { |
|
|
|
return (this.removeFile(path)) |
|
|
|
resolve(this.removeFile(path)) |
|
|
|
} else { |
|
|
|
} else { |
|
|
|
const items = await window.remixFileSystem.readdir(path) |
|
|
|
const items = window.remixFileSystem.readdirSync(path) |
|
|
|
if (items.length !== 0) { |
|
|
|
if (items.length !== 0) { |
|
|
|
for (const item of items) { |
|
|
|
items.forEach((item, index) => { |
|
|
|
const curPath = `${path}${path.endsWith('/') ? '' : '/'}${item}` |
|
|
|
const curPath = `${path}${path.endsWith('/') ? '' : '/'}${item}` |
|
|
|
if ((await window.remixFileSystem.stat(curPath)).isDirectory()) { // delete folder
|
|
|
|
if (window.remixFileSystem.statSync(curPath).isDirectory()) { // delete folder
|
|
|
|
this.remove(curPath) |
|
|
|
this.remove(curPath) |
|
|
|
} else { // delete file
|
|
|
|
} else { // delete file
|
|
|
|
this.removeFile(curPath) |
|
|
|
this.removeFile(curPath) |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
}) |
|
|
|
|
|
|
|
if (window.remixFileSystem.readdirSync(path).length === 0) window.remixFileSystem.rmdirSync(path, console.log) |
|
|
|
|
|
|
|
} else { |
|
|
|
|
|
|
|
// folder is empty
|
|
|
|
|
|
|
|
window.remixFileSystem.rmdirSync(path, console.log) |
|
|
|
|
|
|
|
} |
|
|
|
} |
|
|
|
this.event.emit('fileRemoved', this._normalizePath(path)) |
|
|
|
if (await window.remixFileSystem.readdir(path).length === 0) await window.remixFileSystem.rmdir(path) |
|
|
|
|
|
|
|
} else { |
|
|
|
|
|
|
|
// folder is empty
|
|
|
|
|
|
|
|
await window.remixFileSystem.rmdirSync(path) |
|
|
|
} |
|
|
|
} |
|
|
|
} catch (e) { |
|
|
|
this.event.emit('fileRemoved', this._normalizePath(path)) |
|
|
|
console.log(e) |
|
|
|
|
|
|
|
return resolve(false) |
|
|
|
|
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
} catch (e) { |
|
|
|
|
|
|
|
console.log(e) |
|
|
|
|
|
|
|
return false |
|
|
|
} |
|
|
|
} |
|
|
|
return resolve(true) |
|
|
|
} |
|
|
|
}) |
|
|
|
|
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
/** |
|
|
|
/** |
|
|
@ -207,28 +209,28 @@ class FileProvider { |
|
|
|
* @param {Function} visitFile is a function called for each visited files |
|
|
|
* @param {Function} visitFile is a function called for each visited files |
|
|
|
* @param {Function} visitFolder is a function called for each visited folders |
|
|
|
* @param {Function} visitFolder is a function called for each visited folders |
|
|
|
*/ |
|
|
|
*/ |
|
|
|
_copyFolderToJsonInternal (path, visitFile, visitFolder) { |
|
|
|
async _copyFolderToJsonInternal (path, visitFile, visitFolder) { |
|
|
|
visitFile = visitFile || (() => {}) |
|
|
|
/* visitFile = visitFile || (() => { }) |
|
|
|
visitFolder = visitFolder || (() => {}) |
|
|
|
visitFolder = visitFolder || (() => { }) |
|
|
|
return new Promise((resolve, reject) => { |
|
|
|
return new Promise((resolve, reject) => { |
|
|
|
const json = {} |
|
|
|
const json = {} |
|
|
|
path = this.removePrefix(path) |
|
|
|
path = this.removePrefix(path) |
|
|
|
if (window.remixFileSystem.existsSync(path)) { |
|
|
|
if (window.remixFileSystem.exists(path)) { |
|
|
|
try { |
|
|
|
try { |
|
|
|
const items = window.remixFileSystem.readdirSync(path) |
|
|
|
const items = await window.remixFileSystem.readdir(path) |
|
|
|
visitFolder({ path }) |
|
|
|
visitFolder({ path }) |
|
|
|
if (items.length !== 0) { |
|
|
|
if (items.length !== 0) { |
|
|
|
items.forEach(async (item, index) => { |
|
|
|
for (const item of items) { |
|
|
|
const file = {} |
|
|
|
const file = {} |
|
|
|
const curPath = `${path}${path.endsWith('/') ? '' : '/'}${item}` |
|
|
|
const curPath = `${path}${path.endsWith('/') ? '' : '/'}${item}` |
|
|
|
if (window.remixFileSystem.statSync(curPath).isDirectory()) { |
|
|
|
if (await window.remixFileSystem.stat(curPath).isDirectory()) { |
|
|
|
file.children = await this._copyFolderToJsonInternal(curPath, visitFile, visitFolder) |
|
|
|
file.children = await this._copyFolderToJsonInternal(curPath, visitFile, visitFolder) |
|
|
|
} else { |
|
|
|
} else { |
|
|
|
file.content = window.remixFileSystem.readFileSync(curPath, 'utf8') |
|
|
|
file.content = window.remixFileSystem.readFileSync(curPath, 'utf8') |
|
|
|
visitFile({ path: curPath, content: file.content }) |
|
|
|
visitFile({ path: curPath, content: file.content }) |
|
|
|
} |
|
|
|
} |
|
|
|
json[curPath] = file |
|
|
|
json[curPath] = file |
|
|
|
}) |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} catch (e) { |
|
|
|
} catch (e) { |
|
|
|
console.log(e) |
|
|
|
console.log(e) |
|
|
@ -236,7 +238,7 @@ class FileProvider { |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
return resolve(json) |
|
|
|
return resolve(json) |
|
|
|
}) |
|
|
|
}) */ |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
/** |
|
|
|
/** |
|
|
@ -245,26 +247,26 @@ class FileProvider { |
|
|
|
* @param {Function} visitFile is a function called for each visited files |
|
|
|
* @param {Function} visitFile is a function called for each visited files |
|
|
|
* @param {Function} visitFolder is a function called for each visited folders |
|
|
|
* @param {Function} visitFolder is a function called for each visited folders |
|
|
|
*/ |
|
|
|
*/ |
|
|
|
copyFolderToJson (path, visitFile, visitFolder) { |
|
|
|
async copyFolderToJson (path, visitFile, visitFolder) { |
|
|
|
visitFile = visitFile || (() => {}) |
|
|
|
visitFile = visitFile || (() => { }) |
|
|
|
visitFolder = visitFolder || (() => {}) |
|
|
|
visitFolder = visitFolder || (() => { }) |
|
|
|
return this._copyFolderToJsonInternal(path, visitFile, visitFolder) |
|
|
|
return await this._copyFolderToJsonInternal(path, visitFile, visitFolder) |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
removeFile (path) { |
|
|
|
async removeFile (path) { |
|
|
|
path = this.removePrefix(path) |
|
|
|
path = this.removePrefix(path) |
|
|
|
if (window.remixFileSystem.existsSync(path) && !window.remixFileSystem.statSync(path).isDirectory()) { |
|
|
|
if (await window.remixFileSystem.exists(path) && !(await window.remixFileSystem.stat(path)).isDirectory()) { |
|
|
|
window.remixFileSystem.unlinkSync(path, console.log) |
|
|
|
await window.remixFileSystem.unlink(path) |
|
|
|
this.event.emit('fileRemoved', this._normalizePath(path)) |
|
|
|
this.event.emit('fileRemoved', this._normalizePath(path)) |
|
|
|
return true |
|
|
|
return true |
|
|
|
} else return false |
|
|
|
} else return false |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
rename (oldPath, newPath, isFolder) { |
|
|
|
async rename (oldPath, newPath, isFolder) { |
|
|
|
var unprefixedoldPath = this.removePrefix(oldPath) |
|
|
|
var unprefixedoldPath = this.removePrefix(oldPath) |
|
|
|
var unprefixednewPath = this.removePrefix(newPath) |
|
|
|
var unprefixednewPath = this.removePrefix(newPath) |
|
|
|
if (this._exists(unprefixedoldPath)) { |
|
|
|
if (await this._exists(unprefixedoldPath)) { |
|
|
|
window.remixFileSystem.renameSync(unprefixedoldPath, unprefixednewPath) |
|
|
|
await window.remixFileSystem.rename(unprefixedoldPath, unprefixednewPath) |
|
|
|
this.event.emit('fileRenamed', |
|
|
|
this.event.emit('fileRenamed', |
|
|
|
this._normalizePath(unprefixedoldPath), |
|
|
|
this._normalizePath(unprefixedoldPath), |
|
|
|
this._normalizePath(unprefixednewPath), |
|
|
|
this._normalizePath(unprefixednewPath), |
|
|
@ -275,24 +277,37 @@ class FileProvider { |
|
|
|
return false |
|
|
|
return false |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
resolveDirectory (path, callback) { |
|
|
|
async resolveDirectory (path, cb) { |
|
|
|
path = this.removePrefix(path) |
|
|
|
path = this.removePrefix(path) |
|
|
|
|
|
|
|
console.log('resolve', path) |
|
|
|
if (path.indexOf('/') !== 0) path = '/' + path |
|
|
|
if (path.indexOf('/') !== 0) path = '/' + path |
|
|
|
|
|
|
|
try { |
|
|
|
window.remixFileSystem.readdir(path, (error, files) => { |
|
|
|
const files = await window.remixFileSystem.readdir(path) |
|
|
|
var ret = {} |
|
|
|
const ret = {} |
|
|
|
|
|
|
|
|
|
|
|
if (files) { |
|
|
|
if (files) { |
|
|
|
files.forEach(element => { |
|
|
|
for (let element of files) { |
|
|
|
|
|
|
|
console.log(path, element) |
|
|
|
path = path.replace(/^\/|\/$/g, '') // remove first and last slash
|
|
|
|
path = path.replace(/^\/|\/$/g, '') // remove first and last slash
|
|
|
|
element = element.replace(/^\/|\/$/g, '') // remove first and last slash
|
|
|
|
element = element.replace(/^\/|\/$/g, '') // remove first and last slash
|
|
|
|
const absPath = (path === '/' ? '' : path) + '/' + element |
|
|
|
const absPath = (path === '/' ? '' : path) + '/' + element |
|
|
|
ret[absPath.indexOf('/') === 0 ? absPath.substr(1, absPath.length) : absPath] = { isDirectory: window.remixFileSystem.statSync(absPath).isDirectory() } |
|
|
|
ret[absPath.indexOf('/') === 0 ? absPath.substr(1, absPath.length) : absPath] = { isDirectory: (await window.remixFileSystem.stat(this.addSlash(absPath))).isDirectory() } |
|
|
|
// ^ ret does not accept path starting with '/'
|
|
|
|
// ^ ret does not accept path starting with '/'
|
|
|
|
}) |
|
|
|
console.log(ret) |
|
|
|
|
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
callback(error, ret) |
|
|
|
console.log('FILES', ret, files) |
|
|
|
}) |
|
|
|
if (cb) cb(null, ret) |
|
|
|
|
|
|
|
return ret |
|
|
|
|
|
|
|
} catch (error) { |
|
|
|
|
|
|
|
if (cb) cb(error, null) |
|
|
|
|
|
|
|
throw new Error(error) |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
addSlash (file) { |
|
|
|
|
|
|
|
if (!file.startsWith('/'))file = '/' + file |
|
|
|
|
|
|
|
return file |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
removePrefix (path) { |
|
|
|
removePrefix (path) { |
|
|
|