##// END OF EJS Templates
General cleanup of kernelmanger.MultiKernelManager.
Brian E. Granger -
Show More
@@ -330,7 +330,7 b' class MainKernelHandler(AuthenticatedHandler):'
330 @web.authenticated
330 @web.authenticated
331 def get(self):
331 def get(self):
332 km = self.application.kernel_manager
332 km = self.application.kernel_manager
333 self.finish(jsonapi.dumps(km.kernel_ids))
333 self.finish(jsonapi.dumps(km.list_kernel_ids()))
334
334
335 @web.authenticated
335 @web.authenticated
336 def post(self):
336 def post(self):
@@ -63,20 +63,18 b' class MultiKernelManager(LoggingConfigurable):'
63
63
64 _kernels = Dict()
64 _kernels = Dict()
65
65
66 @property
66 def list_kernel_ids(self):
67 def kernel_ids(self):
68 """Return a list of the kernel ids of the active kernels."""
67 """Return a list of the kernel ids of the active kernels."""
69 return self._kernels.keys()
68 # Create a copy so we can iterate over kernels in operations
69 # that delete keys.
70 return list(self._kernels.keys())
70
71
71 def __len__(self):
72 def __len__(self):
72 """Return the number of running kernels."""
73 """Return the number of running kernels."""
73 return len(self.kernel_ids)
74 return len(self.list_kernel_ids())
74
75
75 def __contains__(self, kernel_id):
76 def __contains__(self, kernel_id):
76 if kernel_id in self.kernel_ids:
77 return kernel_id in self._kernels
77 return True
78 else:
79 return False
80
78
81 def start_kernel(self, **kwargs):
79 def start_kernel(self, **kwargs):
82 """Start a new kernel.
80 """Start a new kernel.
@@ -109,6 +107,11 b' class MultiKernelManager(LoggingConfigurable):'
109 self.get_kernel(kernel_id).shutdown_kernel()
107 self.get_kernel(kernel_id).shutdown_kernel()
110 del self._kernels[kernel_id]
108 del self._kernels[kernel_id]
111
109
110 def shutdown_all(self):
111 """Shutdown all kernels."""
112 for kid in self.list_kernel_ids():
113 self.shutdown_kernel(kid)
114
112 def kill_kernel(self, kernel_id):
115 def kill_kernel(self, kernel_id):
113 """Kill a kernel by its kernel uuid.
116 """Kill a kernel by its kernel uuid.
114
117
@@ -120,6 +123,11 b' class MultiKernelManager(LoggingConfigurable):'
120 self.get_kernel(kernel_id).kill_kernel()
123 self.get_kernel(kernel_id).kill_kernel()
121 del self._kernels[kernel_id]
124 del self._kernels[kernel_id]
122
125
126 def kill_all(self):
127 """Kill all kernels."""
128 for kid in self.list_kernel_ids():
129 self.kill_kernel(kid)
130
123 def interrupt_kernel(self, kernel_id):
131 def interrupt_kernel(self, kernel_id):
124 """Interrupt (SIGINT) the kernel by its uuid.
132 """Interrupt (SIGINT) the kernel by its uuid.
125
133
@@ -167,8 +175,8 b' class MultiKernelManager(LoggingConfigurable):'
167 else:
175 else:
168 raise KeyError("Kernel with id not found: %s" % kernel_id)
176 raise KeyError("Kernel with id not found: %s" % kernel_id)
169
177
170 def get_kernel_ports(self, kernel_id):
178 def get_connection_data(self, kernel_id):
171 """Return a dictionary of ports for a kernel.
179 """Return a dictionary of connection data for a kernel.
172
180
173 Parameters
181 Parameters
174 ==========
182 ==========
@@ -177,21 +185,29 b' class MultiKernelManager(LoggingConfigurable):'
177
185
178 Returns
186 Returns
179 =======
187 =======
180 port_dict : dict
188 connection_dict : dict
181 A dict of key, value pairs where the keys are the names
189 A dict of the information needed to connect to a kernel.
182 (stdin_port,iopub_port,shell_port) and the values are the
190 This includes the ip address and the integer port
183 integer port numbers for those channels.
191 numbers of the different channels (stdin_port, iopub_port,
192 shell_port, hb_port).
184 """
193 """
185 # this will raise a KeyError if not found:
186 km = self.get_kernel(kernel_id)
194 km = self.get_kernel(kernel_id)
187 return dict(shell_port=km.shell_port,
195 return dict(ip=km.ip,
196 shell_port=km.shell_port,
188 iopub_port=km.iopub_port,
197 iopub_port=km.iopub_port,
189 stdin_port=km.stdin_port,
198 stdin_port=km.stdin_port,
190 hb_port=km.hb_port,
199 hb_port=km.hb_port,
191 )
200 )
192
201
193 def get_kernel_ip(self, kernel_id):
202 def create_connected_stream(self, ip, port, socket_type):
194 """Return ip address for a kernel.
203 sock = self.context.socket(socket_type)
204 addr = "tcp://%s:%i" % (ip, port)
205 self.log.info("Connecting to: %s" % addr)
206 sock.connect(addr)
207 return ZMQStream(sock)
208
209 def create_iopub_stream(self, kernel_id):
210 """Return a ZMQStream object connected to the iopub channel.
195
211
196 Parameters
212 Parameters
197 ==========
213 ==========
@@ -200,35 +216,49 b' class MultiKernelManager(LoggingConfigurable):'
200
216
201 Returns
217 Returns
202 =======
218 =======
203 ip : str
219 stream : ZMQStream
204 The ip address of the kernel.
205 """
220 """
206 return self.get_kernel(kernel_id).ip
221 kdata = self.get_connection_data(kernel_id)
207
222 iopub_stream = self.create_connected_stream(
208 def create_connected_stream(self, ip, port, socket_type):
223 kdata['ip'], kdata['iopub_port'], zmq.SUB
209 sock = self.context.socket(socket_type)
224 )
210 addr = "tcp://%s:%i" % (ip, port)
211 self.log.info("Connecting to: %s" % addr)
212 sock.connect(addr)
213 return ZMQStream(sock)
214
215 def create_iopub_stream(self, kernel_id):
216 ip = self.get_kernel_ip(kernel_id)
217 ports = self.get_kernel_ports(kernel_id)
218 iopub_stream = self.create_connected_stream(ip, ports['iopub_port'], zmq.SUB)
219 iopub_stream.socket.setsockopt(zmq.SUBSCRIBE, b'')
225 iopub_stream.socket.setsockopt(zmq.SUBSCRIBE, b'')
220 return iopub_stream
226 return iopub_stream
221
227
222 def create_shell_stream(self, kernel_id):
228 def create_shell_stream(self, kernel_id):
223 ip = self.get_kernel_ip(kernel_id)
229 """Return a ZMQStream object connected to the shell channel.
224 ports = self.get_kernel_ports(kernel_id)
230
225 shell_stream = self.create_connected_stream(ip, ports['shell_port'], zmq.DEALER)
231 Parameters
232 ==========
233 kernel_id : uuid
234 The id of the kernel.
235
236 Returns
237 =======
238 stream : ZMQStream
239 """
240 kdata = self.get_connection_data(kernel_id)
241 shell_stream = self.create_connected_stream(
242 kdata['ip'], kdata['shell_port'], zmq.DEALER
243 )
226 return shell_stream
244 return shell_stream
227
245
228 def create_hb_stream(self, kernel_id):
246 def create_hb_stream(self, kernel_id):
229 ip = self.get_kernel_ip(kernel_id)
247 """Return a ZMQStream object connected to the hb channel.
230 ports = self.get_kernel_ports(kernel_id)
248
231 hb_stream = self.create_connected_stream(ip, ports['hb_port'], zmq.REQ)
249 Parameters
250 ==========
251 kernel_id : uuid
252 The id of the kernel.
253
254 Returns
255 =======
256 stream : ZMQStream
257 """
258 kdata = self.get_connection_data(kernel_id)
259 hb_stream = self.create_connected_stream(
260 kdata['ip'], kdata['hb_port'], zmq.REQ
261 )
232 return hb_stream
262 return hb_stream
233
263
234
264
@@ -591,16 +591,13 b' class NotebookApp(BaseIPythonApplication):'
591 self.init_signal()
591 self.init_signal()
592
592
593 def cleanup_kernels(self):
593 def cleanup_kernels(self):
594 """shutdown all kernels
594 """Shutdown all kernels.
595
595
596 The kernels will shutdown themselves when this process no longer exists,
596 The kernels will shutdown themselves when this process no longer exists,
597 but explicit shutdown allows the KernelManagers to cleanup the connection files.
597 but explicit shutdown allows the KernelManagers to cleanup the connection files.
598 """
598 """
599 self.log.info('Shutting down kernels')
599 self.log.info('Shutting down kernels')
600 km = self.kernel_manager
600 self.kernel_manager.shutdown_all()
601 # copy list, since shutdown_kernel deletes keys
602 for kid in list(km.kernel_ids):
603 km.shutdown_kernel(kid)
604
601
605 def start(self):
602 def start(self):
606 ip = self.ip if self.ip else '[all ip addresses on your system]'
603 ip = self.ip if self.ip else '[all ip addresses on your system]'
@@ -10,17 +10,21 b' class TestKernelManager(TestCase):'
10 km = MultiKernelManager()
10 km = MultiKernelManager()
11 kid = km.start_kernel()
11 kid = km.start_kernel()
12 self.assertTrue(kid in km)
12 self.assertTrue(kid in km)
13 self.assertTrue(kid in km.list_kernel_ids())
13 self.assertEqual(len(km),1)
14 self.assertEqual(len(km),1)
15 new_kid = km.restart_kernel(kid)
16 self.assertTrue(kid, new_kid)
17 km.interrupt_kernel(kid)
14 km.kill_kernel(kid)
18 km.kill_kernel(kid)
15 self.assertTrue(not kid in km)
19 self.assertTrue(not kid in km)
16
20
17 kid = km.start_kernel()
21 kid = km.start_kernel()
18 self.assertEqual('127.0.0.1',km.get_kernel_ip(kid))
22 cdata = km.get_connection_data(kid)
19 port_dict = km.get_kernel_ports(kid)
23 self.assertEqual('127.0.0.1', cdata['ip'])
20 self.assertTrue('stdin_port' in port_dict)
24 self.assertTrue('stdin_port' in cdata)
21 self.assertTrue('iopub_port' in port_dict)
25 self.assertTrue('iopub_port' in cdata)
22 self.assertTrue('shell_port' in port_dict)
26 self.assertTrue('shell_port' in cdata)
23 self.assertTrue('hb_port' in port_dict)
27 self.assertTrue('hb_port' in cdata)
24 km.get_kernel(kid)
28 km.get_kernel(kid)
25 km.kill_kernel(kid)
29 km.kill_kernel(kid)
26
30
General Comments 0
You need to be logged in to leave comments. Login now