##// END OF EJS Templates
Add kernel_info method to InProcessShellChannel
Christophe Pradal -
Show More
@@ -1,195 +1,201 b''
1 """ A kernel client for in-process kernels. """
1 """ A kernel client for in-process kernels. """
2
2
3 #-----------------------------------------------------------------------------
3 #-----------------------------------------------------------------------------
4 # Copyright (C) 2012 The IPython Development Team
4 # Copyright (C) 2012 The IPython Development Team
5 #
5 #
6 # Distributed under the terms of the BSD License. The full license is in
6 # Distributed under the terms of the BSD License. The full license is in
7 # the file COPYING, distributed as part of this software.
7 # the file COPYING, distributed as part of this software.
8 #-----------------------------------------------------------------------------
8 #-----------------------------------------------------------------------------
9
9
10 #-----------------------------------------------------------------------------
10 #-----------------------------------------------------------------------------
11 # Imports
11 # Imports
12 #-----------------------------------------------------------------------------
12 #-----------------------------------------------------------------------------
13
13
14 # IPython imports
14 # IPython imports
15 from IPython.kernel.channelsabc import (
15 from IPython.kernel.channelsabc import (
16 ShellChannelABC, IOPubChannelABC,
16 ShellChannelABC, IOPubChannelABC,
17 HBChannelABC, StdInChannelABC,
17 HBChannelABC, StdInChannelABC,
18 )
18 )
19
19
20 # Local imports
20 # Local imports
21 from .socket import DummySocket
21 from .socket import DummySocket
22
22
23 #-----------------------------------------------------------------------------
23 #-----------------------------------------------------------------------------
24 # Channel classes
24 # Channel classes
25 #-----------------------------------------------------------------------------
25 #-----------------------------------------------------------------------------
26
26
27 class InProcessChannel(object):
27 class InProcessChannel(object):
28 """Base class for in-process channels."""
28 """Base class for in-process channels."""
29 proxy_methods = []
29 proxy_methods = []
30
30
31 def __init__(self, client):
31 def __init__(self, client):
32 super(InProcessChannel, self).__init__()
32 super(InProcessChannel, self).__init__()
33 self.client = client
33 self.client = client
34 self._is_alive = False
34 self._is_alive = False
35
35
36 #--------------------------------------------------------------------------
36 #--------------------------------------------------------------------------
37 # Channel interface
37 # Channel interface
38 #--------------------------------------------------------------------------
38 #--------------------------------------------------------------------------
39
39
40 def is_alive(self):
40 def is_alive(self):
41 return self._is_alive
41 return self._is_alive
42
42
43 def start(self):
43 def start(self):
44 self._is_alive = True
44 self._is_alive = True
45
45
46 def stop(self):
46 def stop(self):
47 self._is_alive = False
47 self._is_alive = False
48
48
49 def call_handlers(self, msg):
49 def call_handlers(self, msg):
50 """ This method is called in the main thread when a message arrives.
50 """ This method is called in the main thread when a message arrives.
51
51
52 Subclasses should override this method to handle incoming messages.
52 Subclasses should override this method to handle incoming messages.
53 """
53 """
54 raise NotImplementedError('call_handlers must be defined in a subclass.')
54 raise NotImplementedError('call_handlers must be defined in a subclass.')
55
55
56 #--------------------------------------------------------------------------
56 #--------------------------------------------------------------------------
57 # InProcessChannel interface
57 # InProcessChannel interface
58 #--------------------------------------------------------------------------
58 #--------------------------------------------------------------------------
59
59
60 def call_handlers_later(self, *args, **kwds):
60 def call_handlers_later(self, *args, **kwds):
61 """ Call the message handlers later.
61 """ Call the message handlers later.
62
62
63 The default implementation just calls the handlers immediately, but this
63 The default implementation just calls the handlers immediately, but this
64 method exists so that GUI toolkits can defer calling the handlers until
64 method exists so that GUI toolkits can defer calling the handlers until
65 after the event loop has run, as expected by GUI frontends.
65 after the event loop has run, as expected by GUI frontends.
66 """
66 """
67 self.call_handlers(*args, **kwds)
67 self.call_handlers(*args, **kwds)
68
68
69 def process_events(self):
69 def process_events(self):
70 """ Process any pending GUI events.
70 """ Process any pending GUI events.
71
71
72 This method will be never be called from a frontend without an event
72 This method will be never be called from a frontend without an event
73 loop (e.g., a terminal frontend).
73 loop (e.g., a terminal frontend).
74 """
74 """
75 raise NotImplementedError
75 raise NotImplementedError
76
76
77
77
78 class InProcessShellChannel(InProcessChannel):
78 class InProcessShellChannel(InProcessChannel):
79 """See `IPython.kernel.channels.ShellChannel` for docstrings."""
79 """See `IPython.kernel.channels.ShellChannel` for docstrings."""
80
80
81 # flag for whether execute requests should be allowed to call raw_input
81 # flag for whether execute requests should be allowed to call raw_input
82 allow_stdin = True
82 allow_stdin = True
83 proxy_methods = [
83 proxy_methods = [
84 'execute',
84 'execute',
85 'complete',
85 'complete',
86 'object_info',
86 'object_info',
87 'history',
87 'history',
88 'shutdown',
88 'shutdown',
89 'kernel_info',
89 'kernel_info',
90 ]
90 ]
91
91
92 #--------------------------------------------------------------------------
92 #--------------------------------------------------------------------------
93 # ShellChannel interface
93 # ShellChannel interface
94 #--------------------------------------------------------------------------
94 #--------------------------------------------------------------------------
95
95
96 def execute(self, code, silent=False, store_history=True,
96 def execute(self, code, silent=False, store_history=True,
97 user_variables=[], user_expressions={}, allow_stdin=None):
97 user_variables=[], user_expressions={}, allow_stdin=None):
98 if allow_stdin is None:
98 if allow_stdin is None:
99 allow_stdin = self.allow_stdin
99 allow_stdin = self.allow_stdin
100 content = dict(code=code, silent=silent, store_history=store_history,
100 content = dict(code=code, silent=silent, store_history=store_history,
101 user_variables=user_variables,
101 user_variables=user_variables,
102 user_expressions=user_expressions,
102 user_expressions=user_expressions,
103 allow_stdin=allow_stdin)
103 allow_stdin=allow_stdin)
104 msg = self.client.session.msg('execute_request', content)
104 msg = self.client.session.msg('execute_request', content)
105 self._dispatch_to_kernel(msg)
105 self._dispatch_to_kernel(msg)
106 return msg['header']['msg_id']
106 return msg['header']['msg_id']
107
107
108 def complete(self, text, line, cursor_pos, block=None):
108 def complete(self, text, line, cursor_pos, block=None):
109 content = dict(text=text, line=line, block=block, cursor_pos=cursor_pos)
109 content = dict(text=text, line=line, block=block, cursor_pos=cursor_pos)
110 msg = self.client.session.msg('complete_request', content)
110 msg = self.client.session.msg('complete_request', content)
111 self._dispatch_to_kernel(msg)
111 self._dispatch_to_kernel(msg)
112 return msg['header']['msg_id']
112 return msg['header']['msg_id']
113
113
114 def object_info(self, oname, detail_level=0):
114 def object_info(self, oname, detail_level=0):
115 content = dict(oname=oname, detail_level=detail_level)
115 content = dict(oname=oname, detail_level=detail_level)
116 msg = self.client.session.msg('object_info_request', content)
116 msg = self.client.session.msg('object_info_request', content)
117 self._dispatch_to_kernel(msg)
117 self._dispatch_to_kernel(msg)
118 return msg['header']['msg_id']
118 return msg['header']['msg_id']
119
119
120 def history(self, raw=True, output=False, hist_access_type='range', **kwds):
120 def history(self, raw=True, output=False, hist_access_type='range', **kwds):
121 content = dict(raw=raw, output=output,
121 content = dict(raw=raw, output=output,
122 hist_access_type=hist_access_type, **kwds)
122 hist_access_type=hist_access_type, **kwds)
123 msg = self.client.session.msg('history_request', content)
123 msg = self.client.session.msg('history_request', content)
124 self._dispatch_to_kernel(msg)
124 self._dispatch_to_kernel(msg)
125 return msg['header']['msg_id']
125 return msg['header']['msg_id']
126
126
127 def shutdown(self, restart=False):
127 def shutdown(self, restart=False):
128 # FIXME: What to do here?
128 # FIXME: What to do here?
129 raise NotImplementedError('Cannot shutdown in-process kernel')
129 raise NotImplementedError('Cannot shutdown in-process kernel')
130
130
131 def kernel_info(self):
132 """Request kernel info."""
133 msg = self.client.session.msg('kernel_info_request')
134 self._dispatch_to_kernel(msg)
135 return msg['header']['msg_id']
136
131 #--------------------------------------------------------------------------
137 #--------------------------------------------------------------------------
132 # Protected interface
138 # Protected interface
133 #--------------------------------------------------------------------------
139 #--------------------------------------------------------------------------
134
140
135 def _dispatch_to_kernel(self, msg):
141 def _dispatch_to_kernel(self, msg):
136 """ Send a message to the kernel and handle a reply.
142 """ Send a message to the kernel and handle a reply.
137 """
143 """
138 kernel = self.client.kernel
144 kernel = self.client.kernel
139 if kernel is None:
145 if kernel is None:
140 raise RuntimeError('Cannot send request. No kernel exists.')
146 raise RuntimeError('Cannot send request. No kernel exists.')
141
147
142 stream = DummySocket()
148 stream = DummySocket()
143 self.client.session.send(stream, msg)
149 self.client.session.send(stream, msg)
144 msg_parts = stream.recv_multipart()
150 msg_parts = stream.recv_multipart()
145 kernel.dispatch_shell(stream, msg_parts)
151 kernel.dispatch_shell(stream, msg_parts)
146
152
147 idents, reply_msg = self.client.session.recv(stream, copy=False)
153 idents, reply_msg = self.client.session.recv(stream, copy=False)
148 self.call_handlers_later(reply_msg)
154 self.call_handlers_later(reply_msg)
149
155
150
156
151 class InProcessIOPubChannel(InProcessChannel):
157 class InProcessIOPubChannel(InProcessChannel):
152 """See `IPython.kernel.channels.IOPubChannel` for docstrings."""
158 """See `IPython.kernel.channels.IOPubChannel` for docstrings."""
153
159
154 def flush(self, timeout=1.0):
160 def flush(self, timeout=1.0):
155 pass
161 pass
156
162
157
163
158 class InProcessStdInChannel(InProcessChannel):
164 class InProcessStdInChannel(InProcessChannel):
159 """See `IPython.kernel.channels.StdInChannel` for docstrings."""
165 """See `IPython.kernel.channels.StdInChannel` for docstrings."""
160
166
161 proxy_methods = ['input']
167 proxy_methods = ['input']
162
168
163 def input(self, string):
169 def input(self, string):
164 kernel = self.client.kernel
170 kernel = self.client.kernel
165 if kernel is None:
171 if kernel is None:
166 raise RuntimeError('Cannot send input reply. No kernel exists.')
172 raise RuntimeError('Cannot send input reply. No kernel exists.')
167 kernel.raw_input_str = string
173 kernel.raw_input_str = string
168
174
169
175
170 class InProcessHBChannel(InProcessChannel):
176 class InProcessHBChannel(InProcessChannel):
171 """See `IPython.kernel.channels.HBChannel` for docstrings."""
177 """See `IPython.kernel.channels.HBChannel` for docstrings."""
172
178
173 time_to_dead = 3.0
179 time_to_dead = 3.0
174
180
175 def __init__(self, *args, **kwds):
181 def __init__(self, *args, **kwds):
176 super(InProcessHBChannel, self).__init__(*args, **kwds)
182 super(InProcessHBChannel, self).__init__(*args, **kwds)
177 self._pause = True
183 self._pause = True
178
184
179 def pause(self):
185 def pause(self):
180 self._pause = True
186 self._pause = True
181
187
182 def unpause(self):
188 def unpause(self):
183 self._pause = False
189 self._pause = False
184
190
185 def is_beating(self):
191 def is_beating(self):
186 return not self._pause
192 return not self._pause
187
193
188 #-----------------------------------------------------------------------------
194 #-----------------------------------------------------------------------------
189 # ABC Registration
195 # ABC Registration
190 #-----------------------------------------------------------------------------
196 #-----------------------------------------------------------------------------
191
197
192 ShellChannelABC.register(InProcessShellChannel)
198 ShellChannelABC.register(InProcessShellChannel)
193 IOPubChannelABC.register(InProcessIOPubChannel)
199 IOPubChannelABC.register(InProcessIOPubChannel)
194 HBChannelABC.register(InProcessHBChannel)
200 HBChannelABC.register(InProcessHBChannel)
195 StdInChannelABC.register(InProcessStdInChannel)
201 StdInChannelABC.register(InProcessStdInChannel)
General Comments 0
You need to be logged in to leave comments. Login now