1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 from libxyz.core.plugins import BasePlugin
18 from libxyz.core import dsl
19 from libxyz.core.utils import bstring
20 from libxyz.core import Queue
21 from libxyz.ui import lowui
22
23 import libxyz.ui as ui
24
26 "Plugin console"
27
28 NAME = u"console"
29 AUTHOR = u"Max E. Kuznecov <syhpoon@syhpoon.name>"
30 VERSION = u"0.1"
31 BRIEF_DESCRIPTION = u"Interactive management console"
32 FULL_DESCRIPTION = u"Provides interactive management console"
33 NAMESPACE = u"core"
34 DOC = u"Configuration variables:\n"\
35 u"history_depth - Specifies how many entered "\
36 u"commands to keep. Default - 50\n"\
37 u"prompt - Command line prompt. Default - '> '"
38
39 EVENTS = [("show",
40 "Fires upon showing console. Arguments: No."),
41 ("cmd_prev",
42 "Fires when scrolling through history. "\
43 "Arguments: Current command from history buffer"),
44 ("execute",
45 "Fires when typed command is to be executed. "\
46 "Arguments: typed command"),
47 ]
48
50 super(XYZPlugin, self).__init__(xyz)
51
52 self.attr = lambda x: self.xyz.skin.get_palette(u"plugin.console", x)
53
54 self._keys= ui.Keys()
55 self._index = 1
56 self.output = []
57 self.edit = lowui.Edit(self.conf["prompt"], wrap="clip")
58 self._input = lowui.AttrWrap(self.edit, self.attr("input"))
59 self._header = lowui.AttrWrap(lowui.Text(_(u"Management console")),
60 self.attr("header"))
61 self._history = Queue(self.conf["history_depth"])
62
63 self.export(self.show)
64
65
66
68 """
69 Show console window
70 """
71
72 def _get_cmd(k):
73 """
74 Fetch previous command from history
75 """
76
77 if k == self._keys.UP:
78 _i = -1
79 else:
80 _i = 1
81
82 _pos = len(self._history) - 1 + (self._index + _i)
83
84 if _pos < 0:
85 return None
86 elif _pos > len(self._history):
87 return None
88 else:
89 self._index += _i
90
91 if _pos == len(self._history):
92 return ""
93
94 try:
95 cmd = self._history[_pos]
96 except Exception:
97 return None
98 else:
99 return cmd
100
101
102
103 self.fire_event("show")
104 _stop = False
105
106 while True:
107 walker = lowui.SimpleListWalker(self.output)
108 walker.focus = len(walker) - 1
109 lbox = lowui.AttrWrap(lowui.ListBox(walker), self.attr("output"))
110
111 console = lowui.Frame(lbox, header=self._header,
112 footer=self._input, focus_part='footer')
113 dim = self.xyz.screen.get_cols_rows()
114
115 self.xyz.screen.draw_screen(dim, console.render(dim, True))
116
117 data = self.xyz.input.get()
118
119 for k in data:
120 if k in (self._keys.UP, self._keys.DOWN):
121 cmd = _get_cmd(k)
122
123 if cmd is not None:
124 self.fire_event("cmd_prev", cmd)
125 self.edit.set_edit_text("")
126 self.edit.insert_text(cmd)
127 elif k == self._keys.ENTER:
128 self._index = 1
129 chunk = self.edit.get_edit_text()
130 self.edit.set_edit_text("")
131 compiled = None
132
133 if not chunk:
134 continue
135
136 self._history.push(chunk)
137
138 self._write("> %s" % chunk)
139
140 try:
141 compiled = compile(chunk, "<input>", "eval")
142 except Exception, e:
143 self._write(str(e))
144 break
145 else:
146
147 if compiled is None:
148 break
149 else:
150 self.fire_event("execute", chunk)
151
152 chunk = ""
153 try:
154 self._write(
155 eval(compiled, dsl.XYZ.get_env()))
156 except Exception, e:
157 self._write(str(e))
158 elif k == self._keys.ESCAPE:
159 _stop = True
160 break
161 else:
162 self._input.keypress((dim[0],), k)
163
164 if _stop:
165 break
166
167
168
170 """
171 Write text to output
172 """
173
174 self.output.extend([lowui.Text(x) for x in bstring(msg).split("\n")])
175