1
0
mirror of https://github.com/gryf/pentadactyl-pm.git synced 2025-12-22 19:47:58 +01:00

merge new vimperator.io object

This commit is contained in:
Doug Kearns
2007-10-22 02:55:52 +00:00
parent dd3196f0b4
commit 05ab034753
4 changed files with 230 additions and 287 deletions

View File

@@ -237,7 +237,7 @@ vimperator.completion = (function() // {{{
}, //}}} }, //}}}
// TODO: support file:// and \ or / path separators on both platforms // TODO: support file:// and \ or / path separators on both platforms
get_file_completions: function(filter) //{{{ get_file_completions: function(filter)
{ {
// this is now also used as part of the url completion, so the // this is now also used as part of the url completion, so the
// substrings shouldn't be cleared for that case // substrings shouldn't be cleared for that case
@@ -252,35 +252,12 @@ vimperator.completion = (function() // {{{
var compl = matches[2] || ""; var compl = matches[2] || "";
var files = [], mapped = [];
try try
{ {
var fd = vimperator.io.fopen(dir); files = vimperator.io.readDirectory(dir);
} mapped = files.map(function(file) {
catch (e) return [[file.path], file.isDirectory() ? "Directory" : "File"];
{
// thrown if file does not exist
return [];
}
if (!fd)
return [];
try
{
var entries = fd.read();
var separator = fd.path.length == 1 ? "" : /\\/.test(fd.path) ? "\\" : "/";
var new_filter = fd.path + separator + compl;
if (!filter) return entries.map(function(file) {
var path = file.path;
if (file.isDirectory())
path += separator;
return [path, ""];
});
var mapped = entries.map(function(file) {
var path = file.path;
if (file.isDirectory())
path += separator;
return [[path], ""];
}); });
} }
catch (e) catch (e)
@@ -288,8 +265,9 @@ vimperator.completion = (function() // {{{
return []; return [];
} }
return build_longest_starting_substring(mapped, new_filter);
}, //}}} return build_longest_starting_substring(mapped, filter);
},
get_help_completions: function(filter) //{{{ get_help_completions: function(filter) //{{{
{ {

View File

@@ -27,115 +27,141 @@ the provisions above, a recipient may use your version of this file under
the terms of any one of the MPL, the GPL or the LGPL. the terms of any one of the MPL, the GPL or the LGPL.
}}} ***** END LICENSE BLOCK *****/ }}} ***** END LICENSE BLOCK *****/
vimperator.io = {}; vimperator.io = (function()
vimperator.io.fopen = function(path, mode, perms, tmp)
{ {
return new vimperator.io.LocalFile(path, mode, perms, tmp); var environment_service = Components.classes["@mozilla.org/process/environment;1"]
} .getService(Components.interfaces.nsIEnvironment);
vimperator.io.LocalFile = function(file, mode, perms, tmp) // {{{ vimperator.log("Loading vimperator.io");
{
const PERM_IWOTH = 00002; /* write permission, others */
const PERM_IWGRP = 00020; /* write permission, group */
const MODE_RDONLY = 0x01; return {
const MODE_WRONLY = 0x02;
const MODE_RDWR = 0x04;
const MODE_CREATE = 0x08;
const MODE_APPEND = 0x10;
const MODE_TRUNCATE = 0x20;
const MODE_SYNC = 0x40;
const MODE_EXCL = 0x80;
const classes = Components.classes; MODE_RDONLY: 0x01,
const interfaces = Components.interfaces; MODE_WRONLY: 0x02,
MODE_RDWR: 0x04,
MODE_CREATE: 0x08,
MODE_APPEND: 0x10,
MODE_TRUNCATE: 0x20,
MODE_SYNC: 0x40,
MODE_EXCL: 0x80,
const LOCALFILE_CTRID = "@mozilla.org/file/local;1"; expandPath: function(path)
const FILEIN_CTRID = "@mozilla.org/network/file-input-stream;1";
const FILEOUT_CTRID = "@mozilla.org/network/file-output-stream;1";
const SCRIPTSTREAM_CTRID = "@mozilla.org/scriptableinputstream;1";
const nsIFile = interfaces.nsIFile;
const nsILocalFile = interfaces.nsILocalFile;
const nsIFileOutputStream = interfaces.nsIFileOutputStream;
const nsIFileInputStream = interfaces.nsIFileInputStream;
const nsIScriptableInputStream = interfaces.nsIScriptableInputStream;
if (typeof perms == "undefined")
perms = 0666 & ~(PERM_IWOTH | PERM_IWGRP);
if (typeof mode == "string")
{ {
switch (mode) const WINDOWS = navigator.platform == "Win32";
// TODO: proper pathname separator translation like Vim
if (WINDOWS)
path = path.replace('/', '\\', 'g');
// expand "~" to VIMPERATOR_HOME or HOME (USERPROFILE or HOMEDRIVE\HOMEPATH on Windows if HOME is not set)
if (/^~/.test(path))
{ {
case ">": var home = environment_service.get("VIMPERATOR_HOME");
mode = MODE_WRONLY | MODE_CREATE | MODE_TRUNCATE;
break; if (!home)
case ">>": home = environment_service.get("HOME");
mode = MODE_WRONLY | MODE_CREATE | MODE_APPEND;
break; if (WINDOWS && !home)
case "<": home = environment_service.get("USERPROFILE") ||
mode = MODE_RDONLY; environment_service.get("HOMEDRIVE") + environment_service.get("HOMEPATH");
break;
default: path = path.replace("~", home);
throw "Invalid mode ``" + mode + "''"; }
// expand any $ENV vars
var env_vars = path.match(/\$\w+\b/g); // this is naive but so is Vim and we like to be compatible
if (env_vars)
{
var expansion;
for (var i = 0; i < env_vars.length; i++)
{
expansion = environment_service.get(env_vars[i].replace("$", ""));
if (expansion)
path = path.replace(env_vars[i], expansion);
} }
} }
if (typeof file == "string") return path;
},
getPluginDir: function()
{ {
this.localFile = classes[LOCALFILE_CTRID].createInstance(nsILocalFile); var plugin_dir;
this.localFile.initWithPath(file);
if (!this.localFile.exists()) if (navigator.platform == "Win32")
throw "No such file or directory"; plugin_dir = "~/vimperator/plugin";
} else
else if (file instanceof nsILocalFile) plugin_dir = "~/.vimperator/plugin";
plugin_dir = this.getFile(this.expandPath(plugin_dir));
return plugin_dir.exists() && plugin_dir.isDirectory() ? plugin_dir : null;
},
getRCFile: function()
{ {
this.localFile = file; var rc_file1 = this.getFile(this.expandPath("~/.vimperatorrc"));
if (!this.localFile.exists()) var rc_file2 = this.getFile(this.expandPath("~/_vimperatorrc"));
throw "No such file or directory";
if (navigator.platform == "Win32")
[rc_file1, rc_file2] = [rc_file2, rc_file1]
if (rc_file1.exists() && rc_file1.isFile())
return rc_file1;
else if (rc_file2.exists() && rc_file2.isFile())
return rc_file2;
else
return null;
},
// return a nsILocalFile for path where you can call isDirectory(), etc. on
// caller must check with .exists() if the returned file really exists
getFile: function(path)
{
var file = Components.classes["@mozilla.org/file/local;1"].
createInstance(Components.interfaces.nsILocalFile);
file.initWithPath(this.expandPath(path));
return file;
},
// TODO: make secure
// returns a nsILocalFile or null if it could not be created
createTempFile: function()
{
var file = Components.classes["@mozilla.org/file/local;1"].
createInstance(Components.interfaces.nsILocalFile);
if (navigator.platform == "Win32")
{
var dir = environment_service.get("TMP") || environment_service.get("TEMP") || "C:\\";
file.initWithPath(dir + "\\vimperator.tmp");
} }
else else
{ {
throw "bad type for argument |file|."; var dir = environment_service.get("TMP") || environment_service.get("TEMP") || "/tmp/";
file.initWithPath(dir + "/vimperator.tmp");
} }
this.path = this.localFile.path; file.createUnique(Components.interfaces.nsIFile.NORMAL_FILE_TYPE, 0600);
if (!file.exists())
return null;
if (mode & (MODE_WRONLY | MODE_RDWR)) return file;
},
// file is either a full pathname or an instance of file instanceof nsILocalFile
readDirectory: function(file)
{ {
this.outputStream = if (typeof file == "string")
classes[FILEOUT_CTRID].createInstance(nsIFileOutputStream); file = this.getFile(file);
this.outputStream.init(this.localFile, mode, perms, 0); else if (!(file instanceof Components.interfaces.nsILocalFile))
} throw Components.results.NS_ERROR_INVALID_ARG; // FIXME: does not work as expected, just shows undefined: undefined
if (mode & (MODE_RDONLY | MODE_RDWR)) if (file.isDirectory())
{ {
var is = classes[FILEIN_CTRID].createInstance(nsIFileInputStream); var entries = file.directoryEntries;
is.init(this.localFile, mode, perms, tmp);
this.inputStream =
classes[SCRIPTSTREAM_CTRID].createInstance(nsIScriptableInputStream);
this.inputStream.init(is);
}
}
vimperator.io.LocalFile.prototype.write =
function fo_write(buf)
{
if (!("outputStream" in this))
throw "file not open for writing.";
return this.outputStream.write(buf, buf.length);
}
vimperator.io.LocalFile.prototype.read =
function fo_read(max)
{
if (this.localFile.isDirectory())
{
var entries = this.localFile.directoryEntries;
var array = []; var array = [];
while (entries.hasMoreElements()) while (entries.hasMoreElements())
{ {
@@ -145,35 +171,72 @@ function fo_read(max)
} }
return array; return array;
} }
else
return []; // XXX: or should it throw an error, probably yes?
},
if (!("inputStream" in this)) // file is either a full pathname or an instance of file instanceof nsILocalFile
throw "file not open for reading."; // reads a file in "text" mode and returns the string
readFile: function(file)
{
var ifstream = Components.classes["@mozilla.org/network/file-input-stream;1"]
.createInstance(Components.interfaces.nsIFileInputStream);
var icstream = Components.classes["@mozilla.org/intl/converter-input-stream;1"]
.createInstance(Components.interfaces.nsIConverterInputStream);
var av = this.inputStream.available(); var charset = "UTF-8";
if (typeof max == "undefined") if (typeof file == "string")
max = av; file = this.getFile(file);
else if (!(file instanceof Components.interfaces.nsILocalFile))
throw Components.results.NS_ERROR_INVALID_ARG; // FIXME: does not work as expected, just shows undefined: undefined
if (!av) ifstream.init(file, -1, 0, 0);
return null; const replacementChar = Components.interfaces.nsIConverterInputStream.DEFAULT_REPLACEMENT_CHARACTER;
icstream.init(ifstream, charset, 4096, replacementChar); // 4096 bytes buffering
var rv = this.inputStream.read(max); var buffer = "";
return rv; var str = {};
} while (icstream.readString(4096, str) != 0)
buffer += str.value;
vimperator.io.LocalFile.prototype.close = icstream.close();
function fo_close() ifstream.close();
{
if ("outputStream" in this)
this.outputStream.close();
if ("inputStream" in this)
this.inputStream.close();
}
vimperator.io.LocalFile.prototype.flush = return buffer;
function fo_close() },
{
return this.outputStream.flush(); // file is either a full pathname or an instance of file instanceof nsILocalFile
} // default permission = 0644, only used when creating a new file, does not change permissions if the file exists
//}}} // mode can be ">" or ">>" in addition to the normal MODE_* flags
writeFile: function(file, buf, mode, perms)
{
var ofstream = Components.classes["@mozilla.org/network/file-output-stream;1"]
.createInstance(Components.interfaces.nsIFileOutputStream);
var ocstream = Components.classes["@mozilla.org/intl/converter-output-stream;1"]
.createInstance(Components.interfaces.nsIConverterOutputStream);
var charset = "UTF-8"; // Can be any character encoding name that Mozilla supports
if (typeof file == "string")
file = this.getFile(file);
else if (!(file instanceof Components.interfaces.nsILocalFile))
throw Components.results.NS_ERROR_INVALID_ARG; // FIXME: does not work as expected, just shows undefined: undefined
if (mode == ">>")
mode = this.MODE_WRONLY | this.MODE_CREATE | this.MODE_APPEND;
else if (!mode || mode == ">")
mode = this.MODE_WRONLY | this.MODE_CREATE | this.MODE_TRUNCATE;
if (!perms)
perms = 0644;
ofstream.init(file, mode, perms, 0);
ocstream.init(ofstream, charset, 0, 0x0000);
ocstream.writeString(buf);
ocstream.close();
ofstream.close();
}
}
})();
// vim: set fdm=marker sw=4 ts=4 et: // vim: set fdm=marker sw=4 ts=4 et:

View File

@@ -864,14 +864,11 @@ function Mappings() //{{{
if (url.match(/^file:\/\//) || url.match(/^\//)) if (url.match(/^file:\/\//) || url.match(/^\//))
{ {
var stripedFilename = url.replace(/^(file:\/\/)?(.*)/, "$2"); var stripedFilename = url.replace(/^(file:\/\/)?(.*)/, "$2");
var file = vimperator.io.fopen(stripedFilename, '<'); var file = vimperator.io.getFile(stripedFilename);
if (!file) if (!file || !file.isDirectory())
return false; return false;
if (file.localFile.isDirectory())
return true;
else else
return false; return true;
} }
// for all other locations just check if the URL ends with / // for all other locations just check if the URL ends with /
if (url.match(/\/$/)) if (url.match(/\/$/))

View File

@@ -104,87 +104,6 @@ const vimperator = (function() //{{{
vimperator.echo("-- " + str_mode + str_extended + " --"); vimperator.echo("-- " + str_mode + str_extended + " --");
} }
function expandPath(path)
{
const WINDOWS = navigator.platform == "Win32";
// TODO: proper pathname separator translation like Vim
if (WINDOWS)
path = path.replace('/', '\\', 'g');
// expand "~" to VIMPERATOR_HOME or HOME (USERPROFILE or HOMEDRIVE\HOMEPATH on Windows if HOME is not set)
if (/^~/.test(path))
{
var home = environment_service.get("VIMPERATOR_HOME");
if (!home)
home = environment_service.get("HOME");
if (WINDOWS && !home)
home = environment_service.get("USERPROFILE") ||
environment_service.get("HOMEDRIVE") + environment_service.get("HOMEPATH");
path = path.replace("~", home);
}
// expand any $ENV vars
var env_vars = path.match(/\$\w+\b/g); // this is naive but so is Vim and we like to be compatible
if (env_vars)
{
var expansion;
for (var i = 0; i < env_vars.length; i++)
{
expansion = environment_service.get(env_vars[i].replace("$", ""));
if (expansion)
path = path.replace(env_vars[i], expansion);
}
}
return path;
}
// TODO: add this functionality to LocalFile or wait for Scriptable I/O in FUEL
function pathExists(path)
{
var p = Components.classes["@mozilla.org/file/local;1"]
.createInstance(Components.interfaces.nsILocalFile);
p.initWithPath(expandPath(path));
return p.exists();
}
function getPluginDir()
{
var plugin_dir;
if (navigator.platform == "Win32")
plugin_dir = "~/vimperator/plugin";
else
plugin_dir = "~/.vimperator/plugin";
plugin_dir = expandPath(plugin_dir);
return pathExists(plugin_dir) ? plugin_dir : null;
}
function getRCFile()
{
var rc_file1 = expandPath("~/.vimperatorrc");
var rc_file2 = expandPath("~/_vimperatorrc");
if (navigator.platform == "Win32")
[rc_file1, rc_file2] = [rc_file2, rc_file1]
if (pathExists(rc_file1))
return rc_file1;
else if (pathExists(rc_file2))
return rc_file2;
else
return null;
}
/////////////////////////////////////////////////////////////////////////////}}} /////////////////////////////////////////////////////////////////////////////}}}
////////////////////// PUBLIC SECTION ////////////////////////////////////////// ////////////////////// PUBLIC SECTION //////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////////{{{ /////////////////////////////////////////////////////////////////////////////{{{
@@ -652,7 +571,7 @@ const vimperator = (function() //{{{
{ {
const WINDOWS = navigator.platform == "Win32"; // FIXME: duplicated everywhere const WINDOWS = navigator.platform == "Win32"; // FIXME: duplicated everywhere
var fileout = getTempFile(); var fileout = vimperator.io.createTempFile();
if (!fileout) if (!fileout)
return ""; return "";
@@ -664,10 +583,8 @@ const vimperator = (function() //{{{
var filein = null; var filein = null;
if (input) if (input)
{ {
filein = getTempFile(); filein = vimperator.io.createTempFile();
var fdin = vimperator.io.fopen(filein, ">"); vimperator.io.writeFile(filein, input);
fdin.write(input);
fdin.close();
command += " < \"" + filein.path.replace('"', '\\"') + "\""; command += " < \"" + filein.path.replace('"', '\\"') + "\"";
} }
@@ -677,48 +594,38 @@ const vimperator = (function() //{{{
else else
res = this.run("sh", ["-c", command], true); res = this.run("sh", ["-c", command], true);
var fd = vimperator.io.fopen(fileout, "<"); var output = vimperator.io.readFile(fileout);
if (!fd)
return "";
var s = fd.read();
fd.close();
fileout.remove(false); fileout.remove(false);
if (filein) if (filein)
filein.remove(false); filein.remove(false);
// if there is only one \n at the end, chop it off // if there is only one \n at the end, chop it off
if (s && s.indexOf("\n") == s.length-1) if (output && output.indexOf("\n") == output.length-1)
s = s.substr(0, s.length-1); output = output.substr(0, output.length-1);
return s; return output;
}, },
// files which end in .js are sourced as pure javascript files, // files which end in .js are sourced as pure javascript files,
// no need (actually forbidden) to add: js <<EOF ... EOF around those files // no need (actually forbidden) to add: js <<EOF ... EOF around those files
source: function(filename, silent) source: function(filename, silent)
{ {
filename = expandPath(filename); filename = vimperator.io.expandPath(filename);
try try
{ {
var fd = vimperator.io.fopen(filename, "<"); var str = vimperator.io.readFile(filename);
if (!fd)
return;
var s = fd.read();
fd.close();
// handle pure javascript files specially // handle pure javascript files specially
if (filename.search("\.js$") != -1) if (filename.search("\.js$") != -1)
{ {
eval(s); eval(str);
} }
else else
{ {
var heredoc = ""; var heredoc = "";
var heredoc_end = null; // the string which ends the heredoc var heredoc_end = null; // the string which ends the heredoc
s.split("\n").forEach(function(line) str.split("\n").forEach(function(line)
{ {
if (heredoc_end) // we already are in a heredoc if (heredoc_end) // we already are in a heredoc
{ {
@@ -834,10 +741,10 @@ const vimperator = (function() //{{{
// make sourcing asynchronous, otherwise commands that open new tabs won't work // make sourcing asynchronous, otherwise commands that open new tabs won't work
setTimeout(function() { setTimeout(function() {
var rc_file = getRCFile(); var rc_file = vimperator.io.getRCFile();
if (rc_file) if (rc_file)
vimperator.source(rc_file, true); vimperator.source(rc_file.path, true);
else else
vimperator.log("No user RC file found", 3); vimperator.log("No user RC file found", 3);
@@ -845,15 +752,13 @@ const vimperator = (function() //{{{
var entries = []; var entries = [];
try try
{ {
var plugin_dir = getPluginDir(); var plugin_dir = vimperator.io.getPluginDir();
if (plugin_dir) if (plugin_dir)
{ {
var fd = vimperator.io.fopen(plugin_dir); var files = vimperator.io.readDirectory(plugin_dir.path);
var entries = fd.read();
fd.close();
vimperator.log("Sourcing plugin directory...", 3); vimperator.log("Sourcing plugin directory...", 3);
entries.forEach(function(file) { files.forEach(function(file) {
if (!file.isDirectory()) if (!file.isDirectory())
vimperator.source(file.path, false); vimperator.source(file.path, false);
}); });