2008-09-12 09:31:48 -04:00
|
|
|
import code, os, re, string, StringIO, sys, traceback
|
2008-09-12 10:43:15 -04:00
|
|
|
import buffer, color, completer, lex, method, mode, window
|
2008-09-19 15:57:00 -04:00
|
|
|
from lex import Grammar, PatternRule, RegionRule
|
2008-09-12 09:31:48 -04:00
|
|
|
from point import Point
|
|
|
|
from method import Method
|
|
|
|
from subprocess import Popen, PIPE, STDOUT
|
|
|
|
|
|
|
|
class ShellExec(Method):
|
|
|
|
def _execute(self, w, **vargs):
|
|
|
|
a = w.application
|
|
|
|
if a.completion_window_is_open():
|
|
|
|
a.close_completion_buffer()
|
|
|
|
|
|
|
|
s = w.buffer.make_string()
|
|
|
|
w.mode.history[-1] = s
|
|
|
|
w.mode.history.append('')
|
|
|
|
w.buffer.set_data('')
|
|
|
|
w.mode.hindex = len(w.mode.history) - 1
|
|
|
|
|
|
|
|
if not a.has_buffer_name('*Shell*'):
|
|
|
|
raise Exception, "No shell found!"
|
|
|
|
b = a.bufferlist.get_buffer_by_name('*Shell*')
|
|
|
|
if a.window().buffer is not b:
|
|
|
|
a.switch_buffer(b)
|
2008-10-17 22:03:27 -04:00
|
|
|
b.pipe_write(s + "\n")
|
2008-09-12 09:31:48 -04:00
|
|
|
|
|
|
|
class ShellCancel(Method):
|
|
|
|
def execute(self, w, **vargs):
|
|
|
|
w.application.close_mini_buffer()
|
|
|
|
if w.application.completion_window_is_open():
|
|
|
|
w.application.close_completion_buffer()
|
|
|
|
class ShellClear(Method):
|
|
|
|
def execute(self, w, **vargs):
|
|
|
|
a = w.application
|
|
|
|
if not a.has_buffer_name('*Shell*'):
|
|
|
|
raise Exception, "No shell found!"
|
|
|
|
b = a.bufferlist.get_buffer_by_name('*Shell*')
|
|
|
|
|
|
|
|
class ShellHistoryPrev(Method):
|
|
|
|
def execute(self, w, **vargs):
|
|
|
|
if w.mode.hindex <= 0:
|
|
|
|
w.mode.hindex = 0
|
|
|
|
return
|
|
|
|
elif w.mode.hindex == len(w.mode.history) - 1:
|
|
|
|
w.mode.history[-1] = w.buffer.make_string()
|
|
|
|
w.mode.hindex -= 1
|
|
|
|
w.buffer.set_data(w.mode.history[w.mode.hindex])
|
|
|
|
class ShellHistoryNext(Method):
|
|
|
|
def execute(self, w, **vargs):
|
|
|
|
if w.mode.hindex == len(w.mode.history) - 1:
|
|
|
|
return
|
|
|
|
w.mode.hindex += 1
|
|
|
|
w.buffer.set_data(w.mode.history[w.mode.hindex])
|
|
|
|
|
2008-09-19 12:58:00 -04:00
|
|
|
class ShellTab(Method):
|
|
|
|
def execute(self, w, **vargs):
|
|
|
|
a = w.application
|
|
|
|
s = w.buffer.make_string()
|
|
|
|
|
|
|
|
x = w.logical_cursor().x
|
|
|
|
if not s or s[:x].isspace():
|
|
|
|
w.insert_string_at_cursor(' ' * w.mode.tabwidth)
|
|
|
|
return
|
|
|
|
|
2008-09-19 15:57:00 -04:00
|
|
|
l = lex.Lexer(w.mode, ShellMiniGrammar)
|
2008-09-19 12:58:00 -04:00
|
|
|
tokens = list(l.lex([s]))
|
|
|
|
|
|
|
|
curr_t = None
|
|
|
|
curr_i = None
|
|
|
|
for i in range(0, len(tokens)):
|
|
|
|
t = tokens[i]
|
|
|
|
if t.x < x and t.end_x() >= x:
|
|
|
|
curr_i = i
|
|
|
|
curr_t = t
|
|
|
|
if curr_t is None:
|
|
|
|
return
|
|
|
|
|
2008-09-19 15:57:00 -04:00
|
|
|
if(i == 0) and '/' not in curr_t.string:
|
|
|
|
# we are completing a command
|
|
|
|
candidates = []
|
|
|
|
else:
|
|
|
|
# we are completing a path
|
|
|
|
cwd = os.getcwd()
|
|
|
|
if not cwd.endswith('/'):
|
|
|
|
cwd += '/'
|
|
|
|
path = cwd + curr_t.string
|
|
|
|
(d, name) = os.path.split(path)
|
|
|
|
names = []
|
|
|
|
for x in os.listdir(d):
|
|
|
|
if os.path.isdir(os.path.join(d, x)):
|
|
|
|
names.append(x + '/')
|
|
|
|
else:
|
|
|
|
names.append(x)
|
|
|
|
candidates = [x for x in names if x.startswith(name)]
|
|
|
|
|
|
|
|
s = completer.find_common_string(candidates)[len(name):]
|
|
|
|
w.insert_string_at_cursor(s)
|
|
|
|
mode.mini.use_completion_window(a, name, candidates)
|
2008-09-12 09:31:48 -04:00
|
|
|
|
|
|
|
class ShellBaseMethod(Method):
|
|
|
|
subcls = Method
|
|
|
|
subbuf = '*Shell*'
|
|
|
|
def __init__(self):
|
|
|
|
Method.__init__(self)
|
|
|
|
self.submethod = self.subcls()
|
|
|
|
def _execute(self, w, **vargs):
|
|
|
|
a = w.application
|
|
|
|
if not a.has_buffer_name(self.subbuf):
|
|
|
|
raise Exception, "No shell found!"
|
|
|
|
w2 = a.bufferlist.get_buffer_by_name(self.subbuf).windows[0]
|
|
|
|
self.submethod.execute(w2, **vargs)
|
|
|
|
|
|
|
|
class ShellPageUp(ShellBaseMethod):
|
|
|
|
subcls = method.move.PageUp
|
|
|
|
class ShellPageDown(ShellBaseMethod):
|
|
|
|
subcls = method.move.PageDown
|
|
|
|
class ShellGotoBeginning(ShellBaseMethod):
|
|
|
|
subcls = method.move.GotoBeginning
|
|
|
|
class ShellGotoEnd(ShellBaseMethod):
|
|
|
|
subcls = method.move.GotoEnd
|
|
|
|
|
|
|
|
class OpenShell(Method):
|
|
|
|
'''Evaluate sh expressions'''
|
|
|
|
def execute(self, w, **vargs):
|
|
|
|
a = w.application
|
|
|
|
if not a.has_buffer_name('*Shell*'):
|
2008-10-17 22:03:27 -04:00
|
|
|
b = buffer.PipeBuffer('/bin/bash', [], name="*Shell*", term='xterm')
|
2008-09-12 09:31:48 -04:00
|
|
|
a.add_buffer(b)
|
|
|
|
window.Window(b, a)
|
|
|
|
b = a.bufferlist.get_buffer_by_name('*Shell*')
|
|
|
|
if a.window().buffer is not b:
|
|
|
|
a.switch_buffer(b)
|
|
|
|
f = lambda x: None
|
2008-09-19 12:58:00 -04:00
|
|
|
w.application.open_mini_buffer('>>> ', f, self, None, 'shellmini')
|
2008-09-12 09:31:48 -04:00
|
|
|
|
|
|
|
class ShellMini(mode.Fundamental):
|
|
|
|
modename = 'ShellMini'
|
2008-10-17 22:03:27 -04:00
|
|
|
actions = [ShellExec, ShellClear, ShellCancel,
|
|
|
|
ShellHistoryPrev, ShellHistoryNext,
|
|
|
|
ShellTab,
|
2008-09-12 09:31:48 -04:00
|
|
|
ShellPageUp, ShellPageDown, ShellGotoBeginning, ShellGotoEnd,
|
|
|
|
OpenShell]
|
|
|
|
def __init__(self, w):
|
|
|
|
mode.Fundamental.__init__(self, w)
|
|
|
|
self.saved_input = ""
|
|
|
|
self.history = ['']
|
|
|
|
self.hindex = 0
|
|
|
|
self.add_bindings('shell-exec', ('RETURN',))
|
|
|
|
self.add_bindings('shell-clear', ('C-l',))
|
|
|
|
self.add_bindings('shell-cancel', ('C-]', 'C-g'))
|
|
|
|
self.add_bindings('shell-history-prev', ('C-p', 'UP'))
|
|
|
|
self.add_bindings('shell-history-next', ('C-n', 'DOWN'))
|
2008-09-19 12:58:00 -04:00
|
|
|
self.add_bindings('shell-tab', ('TAB',))
|
2008-09-12 09:31:48 -04:00
|
|
|
self.add_bindings('shell-page-up', ('M-v',))
|
|
|
|
self.add_bindings('shell-page-down', ('C-v',))
|
|
|
|
self.add_bindings('shell-goto-beginning', ('M-<',))
|
|
|
|
self.add_bindings('shell-goto-end', ('M->',))
|
|
|
|
|
|
|
|
install = ShellMini.install
|