##// END OF EJS Templates
Merge pull request #6026 from takluyver/kernelspec-rest-launching...
Min RK -
r17234:b537531d merge
parent child Browse files
Show More
@@ -658,7 +658,9 b' class NotebookApp(BaseIPythonApplication):'
658 kls = import_item(self.notebook_manager_class)
658 kls = import_item(self.notebook_manager_class)
659 self.notebook_manager = kls(parent=self, log=self.log)
659 self.notebook_manager = kls(parent=self, log=self.log)
660 kls = import_item(self.session_manager_class)
660 kls = import_item(self.session_manager_class)
661 self.session_manager = kls(parent=self, log=self.log)
661 self.session_manager = kls(parent=self, log=self.log,
662 kernel_manager=self.kernel_manager,
663 notebook_manager=self.notebook_manager)
662 kls = import_item(self.cluster_manager_class)
664 kls = import_item(self.cluster_manager_class)
663 self.cluster_manager = kls(parent=self, log=self.log)
665 self.cluster_manager = kls(parent=self, log=self.log)
664 self.cluster_manager.update_profiles()
666 self.cluster_manager.update_profiles()
@@ -27,8 +27,16 b' class MainKernelHandler(IPythonHandler):'
27 @web.authenticated
27 @web.authenticated
28 @json_errors
28 @json_errors
29 def post(self):
29 def post(self):
30 model = self.get_json_body()
31 if model is None:
32 raise web.HTTPError(400, "No JSON data provided")
33 try:
34 name = model['name']
35 except KeyError:
36 raise web.HTTPError(400, "Missing field in JSON data: name")
37
30 km = self.kernel_manager
38 km = self.kernel_manager
31 kernel_id = km.start_kernel()
39 kernel_id = km.start_kernel(kernel_name=name)
32 model = km.kernel_model(kernel_id)
40 model = km.kernel_model(kernel_id)
33 location = url_path_join(self.base_url, 'api', 'kernels', kernel_id)
41 location = url_path_join(self.base_url, 'api', 'kernels', kernel_id)
34 self.set_header('Location', url_escape(location))
42 self.set_header('Location', url_escape(location))
@@ -72,8 +72,8 b' class MappingKernelManager(MultiKernelManager):'
72 os_path = os.path.dirname(os_path)
72 os_path = os.path.dirname(os_path)
73 return os_path
73 return os_path
74
74
75 def start_kernel(self, kernel_id=None, path=None, **kwargs):
75 def start_kernel(self, kernel_id=None, path=None, kernel_name='python', **kwargs):
76 """Start a kernel for a session an return its kernel_id.
76 """Start a kernel for a session and return its kernel_id.
77
77
78 Parameters
78 Parameters
79 ----------
79 ----------
@@ -84,12 +84,16 b' class MappingKernelManager(MultiKernelManager):'
84 path : API path
84 path : API path
85 The API path (unicode, '/' delimited) for the cwd.
85 The API path (unicode, '/' delimited) for the cwd.
86 Will be transformed to an OS path relative to root_dir.
86 Will be transformed to an OS path relative to root_dir.
87 kernel_name : str
88 The name identifying which kernel spec to launch. This is ignored if
89 an existing kernel is returned, but it may be checked in the future.
87 """
90 """
88 if kernel_id is None:
91 if kernel_id is None:
89 kwargs['extra_arguments'] = self.kernel_argv
92 kwargs['extra_arguments'] = self.kernel_argv
90 if path is not None:
93 if path is not None:
91 kwargs['cwd'] = self.cwd_for_path(path)
94 kwargs['cwd'] = self.cwd_for_path(path)
92 kernel_id = super(MappingKernelManager, self).start_kernel(**kwargs)
95 kernel_id = super(MappingKernelManager, self).start_kernel(
96 kernel_name=kernel_name, **kwargs)
93 self.log.info("Kernel started: %s" % kernel_id)
97 self.log.info("Kernel started: %s" % kernel_id)
94 self.log.debug("Kernel args: %r" % kwargs)
98 self.log.debug("Kernel args: %r" % kwargs)
95 # register callback for failed auto-restart
99 # register callback for failed auto-restart
@@ -111,7 +115,8 b' class MappingKernelManager(MultiKernelManager):'
111 """Return a dictionary of kernel information described in the
115 """Return a dictionary of kernel information described in the
112 JSON standard model."""
116 JSON standard model."""
113 self._check_kernel_id(kernel_id)
117 self._check_kernel_id(kernel_id)
114 model = {"id":kernel_id}
118 model = {"id":kernel_id,
119 "name": self._kernels[kernel_id].kernel_name}
115 return model
120 return model
116
121
117 def list_kernels(self):
122 def list_kernels(self):
@@ -1,6 +1,6 b''
1 """Test the kernels service API."""
1 """Test the kernels service API."""
2
2
3
3 import json
4 import requests
4 import requests
5
5
6 from IPython.html.utils import url_path_join
6 from IPython.html.utils import url_path_join
@@ -30,8 +30,9 b' class KernelAPI(object):'
30 def get(self, id):
30 def get(self, id):
31 return self._req('GET', id)
31 return self._req('GET', id)
32
32
33 def start(self):
33 def start(self, name='python'):
34 return self._req('POST', '')
34 body = json.dumps({'name': name})
35 return self._req('POST', '', body)
35
36
36 def shutdown(self, id):
37 def shutdown(self, id):
37 return self._req('DELETE', id)
38 return self._req('DELETE', id)
@@ -69,6 +70,7 b' class KernelAPITest(NotebookTestBase):'
69 self.assertEqual(r.status_code, 200)
70 self.assertEqual(r.status_code, 200)
70 assert isinstance(r.json(), list)
71 assert isinstance(r.json(), list)
71 self.assertEqual(r.json()[0]['id'], kern1['id'])
72 self.assertEqual(r.json()[0]['id'], kern1['id'])
73 self.assertEqual(r.json()[0]['name'], kern1['name'])
72
74
73 # create another kernel and check that they both are added to the
75 # create another kernel and check that they both are added to the
74 # list of kernels from a GET request
76 # list of kernels from a GET request
@@ -89,6 +91,7 b' class KernelAPITest(NotebookTestBase):'
89 self.assertEqual(r.headers['Location'], '/api/kernels/'+kern2['id'])
91 self.assertEqual(r.headers['Location'], '/api/kernels/'+kern2['id'])
90 rekern = r.json()
92 rekern = r.json()
91 self.assertEqual(rekern['id'], kern2['id'])
93 self.assertEqual(rekern['id'], kern2['id'])
94 self.assertEqual(rekern['name'], kern2['name'])
92
95
93 def test_kernel_handler(self):
96 def test_kernel_handler(self):
94 # GET kernel with given id
97 # GET kernel with given id
@@ -45,27 +45,28 b' class SessionRootHandler(IPythonHandler):'
45 # Creates a new session
45 # Creates a new session
46 #(unless a session already exists for the named nb)
46 #(unless a session already exists for the named nb)
47 sm = self.session_manager
47 sm = self.session_manager
48 nbm = self.notebook_manager
48
49 km = self.kernel_manager
50 model = self.get_json_body()
49 model = self.get_json_body()
51 if model is None:
50 if model is None:
52 raise web.HTTPError(400, "No JSON data provided")
51 raise web.HTTPError(400, "No JSON data provided")
53 try:
52 try:
54 name = model['notebook']['name']
53 name = model['notebook']['name']
55 except KeyError:
54 except KeyError:
56 raise web.HTTPError(400, "Missing field in JSON data: name")
55 raise web.HTTPError(400, "Missing field in JSON data: notebook.name")
57 try:
56 try:
58 path = model['notebook']['path']
57 path = model['notebook']['path']
59 except KeyError:
58 except KeyError:
60 raise web.HTTPError(400, "Missing field in JSON data: path")
59 raise web.HTTPError(400, "Missing field in JSON data: notebook.path")
60 try:
61 kernel_name = model['kernel']['name']
62 except KeyError:
63 raise web.HTTPError(400, "Missing field in JSON data: kernel.name")
64
61 # Check to see if session exists
65 # Check to see if session exists
62 if sm.session_exists(name=name, path=path):
66 if sm.session_exists(name=name, path=path):
63 model = sm.get_session(name=name, path=path)
67 model = sm.get_session(name=name, path=path)
64 else:
68 else:
65 # allow nbm to specify kernels cwd
69 model = sm.create_session(name=name, path=path, kernel_name=kernel_name)
66 kernel_path = nbm.get_kernel_path(name=name, path=path)
67 kernel_id = km.start_kernel(path=kernel_path)
68 model = sm.create_session(name=name, path=path, kernel_id=kernel_id)
69 location = url_path_join(self.base_url, 'api', 'sessions', model['id'])
70 location = url_path_join(self.base_url, 'api', 'sessions', model['id'])
70 self.set_header('Location', url_escape(location))
71 self.set_header('Location', url_escape(location))
71 self.set_status(201)
72 self.set_status(201)
@@ -108,10 +109,7 b' class SessionHandler(IPythonHandler):'
108 def delete(self, session_id):
109 def delete(self, session_id):
109 # Deletes the session with given session_id
110 # Deletes the session with given session_id
110 sm = self.session_manager
111 sm = self.session_manager
111 km = self.kernel_manager
112 session = sm.get_session(session_id=session_id)
113 sm.delete_session(session_id)
112 sm.delete_session(session_id)
114 km.shutdown_kernel(session['kernel']['id'])
115 self.set_status(204)
113 self.set_status(204)
116 self.finish()
114 self.finish()
117
115
@@ -23,12 +23,16 b' from tornado import web'
23
23
24 from IPython.config.configurable import LoggingConfigurable
24 from IPython.config.configurable import LoggingConfigurable
25 from IPython.utils.py3compat import unicode_type
25 from IPython.utils.py3compat import unicode_type
26 from IPython.utils.traitlets import Instance
26
27
27 #-----------------------------------------------------------------------------
28 #-----------------------------------------------------------------------------
28 # Classes
29 # Classes
29 #-----------------------------------------------------------------------------
30 #-----------------------------------------------------------------------------
30
31
31 class SessionManager(LoggingConfigurable):
32 class SessionManager(LoggingConfigurable):
33
34 kernel_manager = Instance('IPython.html.services.kernels.kernelmanager.MappingKernelManager')
35 notebook_manager = Instance('IPython.html.services.notebooks.nbmanager.NotebookManager', args=())
32
36
33 # Session database initialized below
37 # Session database initialized below
34 _cursor = None
38 _cursor = None
@@ -69,10 +73,15 b' class SessionManager(LoggingConfigurable):'
69 "Create a uuid for a new session"
73 "Create a uuid for a new session"
70 return unicode_type(uuid.uuid4())
74 return unicode_type(uuid.uuid4())
71
75
72 def create_session(self, name=None, path=None, kernel_id=None):
76 def create_session(self, name=None, path=None, kernel_name='python'):
73 """Creates a session and returns its model"""
77 """Creates a session and returns its model"""
74 session_id = self.new_session_id()
78 session_id = self.new_session_id()
75 return self.save_session(session_id, name=name, path=path, kernel_id=kernel_id)
79 # allow nbm to specify kernels cwd
80 kernel_path = self.notebook_manager.get_kernel_path(name=name, path=path)
81 kernel_id = self.kernel_manager.start_kernel(path=kernel_path,
82 kernel_name=kernel_name)
83 return self.save_session(session_id, name=name, path=path,
84 kernel_id=kernel_id)
76
85
77 def save_session(self, session_id, name=None, path=None, kernel_id=None):
86 def save_session(self, session_id, name=None, path=None, kernel_id=None):
78 """Saves the items for the session with the given session_id
87 """Saves the items for the session with the given session_id
@@ -170,8 +179,7 b' class SessionManager(LoggingConfigurable):'
170 query = "UPDATE session SET %s WHERE session_id=?" % (', '.join(sets))
179 query = "UPDATE session SET %s WHERE session_id=?" % (', '.join(sets))
171 self.cursor.execute(query, list(kwargs.values()) + [session_id])
180 self.cursor.execute(query, list(kwargs.values()) + [session_id])
172
181
173 @staticmethod
182 def row_factory(self, cursor, row):
174 def row_factory(cursor, row):
175 """Takes sqlite database session row and turns it into a dictionary"""
183 """Takes sqlite database session row and turns it into a dictionary"""
176 row = sqlite3.Row(cursor, row)
184 row = sqlite3.Row(cursor, row)
177 model = {
185 model = {
@@ -180,9 +188,7 b' class SessionManager(LoggingConfigurable):'
180 'name': row['name'],
188 'name': row['name'],
181 'path': row['path']
189 'path': row['path']
182 },
190 },
183 'kernel': {
191 'kernel': self.kernel_manager.kernel_model(row['kernel_id'])
184 'id': row['kernel_id'],
185 }
186 }
192 }
187 return model
193 return model
188
194
@@ -195,5 +201,6 b' class SessionManager(LoggingConfigurable):'
195 def delete_session(self, session_id):
201 def delete_session(self, session_id):
196 """Deletes the row in the session database with given session_id"""
202 """Deletes the row in the session database with given session_id"""
197 # Check that session exists before deleting
203 # Check that session exists before deleting
198 self.get_session(session_id=session_id)
204 session = self.get_session(session_id=session_id)
205 self.kernel_manager.shutdown_kernel(session['kernel']['id'])
199 self.cursor.execute("DELETE FROM session WHERE session_id=?", (session_id,))
206 self.cursor.execute("DELETE FROM session WHERE session_id=?", (session_id,))
@@ -5,79 +5,101 b' from unittest import TestCase'
5 from tornado import web
5 from tornado import web
6
6
7 from ..sessionmanager import SessionManager
7 from ..sessionmanager import SessionManager
8 from IPython.html.services.kernels.kernelmanager import MappingKernelManager
9
10 class DummyKernel(object):
11 def __init__(self, kernel_name='python'):
12 self.kernel_name = kernel_name
13
14 class DummyMKM(MappingKernelManager):
15 """MappingKernelManager interface that doesn't start kernels, for testing"""
16 def __init__(self, *args, **kwargs):
17 super(DummyMKM, self).__init__(*args, **kwargs)
18 self.id_letters = iter(u'ABCDEFGHIJK')
19
20 def _new_id(self):
21 return next(self.id_letters)
22
23 def start_kernel(self, kernel_id=None, path=None, kernel_name='python', **kwargs):
24 kernel_id = kernel_id or self._new_id()
25 self._kernels[kernel_id] = DummyKernel(kernel_name=kernel_name)
26 return kernel_id
27
28 def shutdown_kernel(self, kernel_id, now=False):
29 del self._kernels[kernel_id]
8
30
9 class TestSessionManager(TestCase):
31 class TestSessionManager(TestCase):
10
32
11 def test_get_session(self):
33 def test_get_session(self):
12 sm = SessionManager()
34 sm = SessionManager(kernel_manager=DummyMKM())
13 session_id = sm.new_session_id()
35 session_id = sm.create_session(name='test.ipynb', path='/path/to/',
14 sm.save_session(session_id=session_id, name='test.ipynb', path='/path/to/', kernel_id='5678')
36 kernel_name='bar')['id']
15 model = sm.get_session(session_id=session_id)
37 model = sm.get_session(session_id=session_id)
16 expected = {'id':session_id, 'notebook':{'name':u'test.ipynb', 'path': u'/path/to/'}, 'kernel':{'id':u'5678'}}
38 expected = {'id':session_id,
39 'notebook':{'name':u'test.ipynb', 'path': u'/path/to/'},
40 'kernel': {'id':u'A', 'name': 'bar'}}
17 self.assertEqual(model, expected)
41 self.assertEqual(model, expected)
18
42
19 def test_bad_get_session(self):
43 def test_bad_get_session(self):
20 # Should raise error if a bad key is passed to the database.
44 # Should raise error if a bad key is passed to the database.
21 sm = SessionManager()
45 sm = SessionManager(kernel_manager=DummyMKM())
22 session_id = sm.new_session_id()
46 session_id = sm.create_session(name='test.ipynb', path='/path/to/',
23 sm.save_session(session_id=session_id, name='test.ipynb', path='/path/to/', kernel_id='5678')
47 kernel_name='foo')['id']
24 self.assertRaises(TypeError, sm.get_session, bad_id=session_id) # Bad keyword
48 self.assertRaises(TypeError, sm.get_session, bad_id=session_id) # Bad keyword
25
49
26 def test_list_sessions(self):
50 def test_list_sessions(self):
27 sm = SessionManager()
51 sm = SessionManager(kernel_manager=DummyMKM())
28 session_id1 = sm.new_session_id()
52 sessions = [
29 session_id2 = sm.new_session_id()
53 sm.create_session(name='test1.ipynb', path='/path/to/1/', kernel_name='python'),
30 session_id3 = sm.new_session_id()
54 sm.create_session(name='test2.ipynb', path='/path/to/2/', kernel_name='python'),
31 sm.save_session(session_id=session_id1, name='test1.ipynb', path='/path/to/1/', kernel_id='5678')
55 sm.create_session(name='test3.ipynb', path='/path/to/3/', kernel_name='python'),
32 sm.save_session(session_id=session_id2, name='test2.ipynb', path='/path/to/2/', kernel_id='5678')
56 ]
33 sm.save_session(session_id=session_id3, name='test3.ipynb', path='/path/to/3/', kernel_id='5678')
34 sessions = sm.list_sessions()
57 sessions = sm.list_sessions()
35 expected = [{'id':session_id1, 'notebook':{'name':u'test1.ipynb',
58 expected = [{'id':sessions[0]['id'], 'notebook':{'name':u'test1.ipynb',
36 'path': u'/path/to/1/'}, 'kernel':{'id':u'5678'}},
59 'path': u'/path/to/1/'}, 'kernel':{'id':u'A', 'name':'python'}},
37 {'id':session_id2, 'notebook': {'name':u'test2.ipynb',
60 {'id':sessions[1]['id'], 'notebook': {'name':u'test2.ipynb',
38 'path': u'/path/to/2/'}, 'kernel':{'id':u'5678'}},
61 'path': u'/path/to/2/'}, 'kernel':{'id':u'B', 'name':'python'}},
39 {'id':session_id3, 'notebook':{'name':u'test3.ipynb',
62 {'id':sessions[2]['id'], 'notebook':{'name':u'test3.ipynb',
40 'path': u'/path/to/3/'}, 'kernel':{'id':u'5678'}}]
63 'path': u'/path/to/3/'}, 'kernel':{'id':u'C', 'name':'python'}}]
41 self.assertEqual(sessions, expected)
64 self.assertEqual(sessions, expected)
42
65
43 def test_update_session(self):
66 def test_update_session(self):
44 sm = SessionManager()
67 sm = SessionManager(kernel_manager=DummyMKM())
45 session_id = sm.new_session_id()
68 session_id = sm.create_session(name='test.ipynb', path='/path/to/',
46 sm.save_session(session_id=session_id, name='test.ipynb', path='/path/to/', kernel_id=None)
69 kernel_name='julia')['id']
47 sm.update_session(session_id, kernel_id='5678')
48 sm.update_session(session_id, name='new_name.ipynb')
70 sm.update_session(session_id, name='new_name.ipynb')
49 model = sm.get_session(session_id=session_id)
71 model = sm.get_session(session_id=session_id)
50 expected = {'id':session_id, 'notebook':{'name':u'new_name.ipynb', 'path': u'/path/to/'}, 'kernel':{'id':u'5678'}}
72 expected = {'id':session_id,
73 'notebook':{'name':u'new_name.ipynb', 'path': u'/path/to/'},
74 'kernel':{'id':u'A', 'name':'julia'}}
51 self.assertEqual(model, expected)
75 self.assertEqual(model, expected)
52
76
53 def test_bad_update_session(self):
77 def test_bad_update_session(self):
54 # try to update a session with a bad keyword ~ raise error
78 # try to update a session with a bad keyword ~ raise error
55 sm = SessionManager()
79 sm = SessionManager(kernel_manager=DummyMKM())
56 session_id = sm.new_session_id()
80 session_id = sm.create_session(name='test.ipynb', path='/path/to/',
57 sm.save_session(session_id=session_id, name='test.ipynb', path='/path/to/', kernel_id='5678')
81 kernel_name='ir')['id']
58 self.assertRaises(TypeError, sm.update_session, session_id=session_id, bad_kw='test.ipynb') # Bad keyword
82 self.assertRaises(TypeError, sm.update_session, session_id=session_id, bad_kw='test.ipynb') # Bad keyword
59
83
60 def test_delete_session(self):
84 def test_delete_session(self):
61 sm = SessionManager()
85 sm = SessionManager(kernel_manager=DummyMKM())
62 session_id1 = sm.new_session_id()
86 sessions = [
63 session_id2 = sm.new_session_id()
87 sm.create_session(name='test1.ipynb', path='/path/to/1/', kernel_name='python'),
64 session_id3 = sm.new_session_id()
88 sm.create_session(name='test2.ipynb', path='/path/to/2/', kernel_name='python'),
65 sm.save_session(session_id=session_id1, name='test1.ipynb', path='/path/to/1/', kernel_id='5678')
89 sm.create_session(name='test3.ipynb', path='/path/to/3/', kernel_name='python'),
66 sm.save_session(session_id=session_id2, name='test2.ipynb', path='/path/to/2/', kernel_id='5678')
90 ]
67 sm.save_session(session_id=session_id3, name='test3.ipynb', path='/path/to/3/', kernel_id='5678')
91 sm.delete_session(sessions[1]['id'])
68 sm.delete_session(session_id2)
92 new_sessions = sm.list_sessions()
69 sessions = sm.list_sessions()
93 expected = [{'id':sessions[0]['id'], 'notebook':{'name':u'test1.ipynb',
70 expected = [{'id':session_id1, 'notebook':{'name':u'test1.ipynb',
94 'path': u'/path/to/1/'}, 'kernel':{'id':u'A', 'name':'python'}},
71 'path': u'/path/to/1/'}, 'kernel':{'id':u'5678'}},
95 {'id':sessions[2]['id'], 'notebook':{'name':u'test3.ipynb',
72 {'id':session_id3, 'notebook':{'name':u'test3.ipynb',
96 'path': u'/path/to/3/'}, 'kernel':{'id':u'C', 'name':'python'}}]
73 'path': u'/path/to/3/'}, 'kernel':{'id':u'5678'}}]
97 self.assertEqual(new_sessions, expected)
74 self.assertEqual(sessions, expected)
75
98
76 def test_bad_delete_session(self):
99 def test_bad_delete_session(self):
77 # try to delete a session that doesn't exist ~ raise error
100 # try to delete a session that doesn't exist ~ raise error
78 sm = SessionManager()
101 sm = SessionManager(kernel_manager=DummyMKM())
79 session_id = sm.new_session_id()
102 sm.create_session(name='test.ipynb', path='/path/to/', kernel_name='python')
80 sm.save_session(session_id=session_id, name='test.ipynb', path='/path/to/', kernel_id='5678')
81 self.assertRaises(TypeError, sm.delete_session, bad_kwarg='23424') # Bad keyword
103 self.assertRaises(TypeError, sm.delete_session, bad_kwarg='23424') # Bad keyword
82 self.assertRaises(web.HTTPError, sm.delete_session, session_id='23424') # nonexistant
104 self.assertRaises(web.HTTPError, sm.delete_session, session_id='23424') # nonexistant
83
105
@@ -37,8 +37,9 b' class SessionAPI(object):'
37 def get(self, id):
37 def get(self, id):
38 return self._req('GET', id)
38 return self._req('GET', id)
39
39
40 def create(self, name, path):
40 def create(self, name, path, kernel_name='python'):
41 body = json.dumps({'notebook': {'name':name, 'path':path}})
41 body = json.dumps({'notebook': {'name':name, 'path':path},
42 'kernel': {'name': kernel_name}})
42 return self._req('POST', '', body)
43 return self._req('POST', '', body)
43
44
44 def modify(self, id, name, path):
45 def modify(self, id, name, path):
@@ -59,6 +59,9 b' define(['
59 this.keyboard_manager = options.keyboard_manager;
59 this.keyboard_manager = options.keyboard_manager;
60 this.save_widget = options.save_widget;
60 this.save_widget = options.save_widget;
61 this.tooltip = new tooltip.Tooltip(this.events);
61 this.tooltip = new tooltip.Tooltip(this.events);
62 // default_kernel_name is a temporary measure while we implement proper
63 // kernel selection and delayed start. Do not rely on it.
64 this.default_kernel_name = 'python';
62 // TODO: This code smells (and the other `= this` line a couple lines down)
65 // TODO: This code smells (and the other `= this` line a couple lines down)
63 // We need a better way to deal with circular instance references.
66 // We need a better way to deal with circular instance references.
64 this.keyboard_manager.notebook = this;
67 this.keyboard_manager.notebook = this;
@@ -1495,7 +1498,12 b' define(['
1495 base_url: this.base_url,
1498 base_url: this.base_url,
1496 notebook_path: this.notebook_path,
1499 notebook_path: this.notebook_path,
1497 notebook_name: this.notebook_name,
1500 notebook_name: this.notebook_name,
1501 // For now, create all sessions with the 'python' kernel, which is the
1502 // default. Later, the user will be able to select kernels. This is
1503 // overridden if KernelManager.kernel_cmd is specified for the server.
1504 kernel_name: this.default_kernel_name,
1498 notebook: this});
1505 notebook: this});
1506
1499 this.session.start($.proxy(this._session_started, this));
1507 this.session.start($.proxy(this._session_started, this));
1500 };
1508 };
1501
1509
@@ -15,13 +15,14 b' define(['
15 * A Kernel Class to communicate with the Python kernel
15 * A Kernel Class to communicate with the Python kernel
16 * @Class Kernel
16 * @Class Kernel
17 */
17 */
18 var Kernel = function (kernel_service_url, notebook) {
18 var Kernel = function (kernel_service_url, notebook, name) {
19 this.events = notebook.events;
19 this.events = notebook.events;
20 this.kernel_id = null;
20 this.kernel_id = null;
21 this.shell_channel = null;
21 this.shell_channel = null;
22 this.iopub_channel = null;
22 this.iopub_channel = null;
23 this.stdin_channel = null;
23 this.stdin_channel = null;
24 this.kernel_service_url = kernel_service_url;
24 this.kernel_service_url = kernel_service_url;
25 this.name = name;
25 this.running = false;
26 this.running = false;
26 this.username = "username";
27 this.username = "username";
27 this.session_id = utils.uuid();
28 this.session_id = utils.uuid();
@@ -15,6 +15,7 b' define(['
15 this.notebook = options.notebook;
15 this.notebook = options.notebook;
16 this.name = options.notebook_name;
16 this.name = options.notebook_name;
17 this.path = options.notebook_path;
17 this.path = options.notebook_path;
18 this.kernel_name = options.kernel_name;
18 this.base_url = options.base_url;
19 this.base_url = options.base_url;
19 };
20 };
20
21
@@ -24,6 +25,9 b' define(['
24 notebook : {
25 notebook : {
25 name : this.name,
26 name : this.name,
26 path : this.path
27 path : this.path
28 },
29 kernel : {
30 name : this.kernel_name
27 }
31 }
28 };
32 };
29 var settings = {
33 var settings = {
@@ -87,7 +91,7 b' define(['
87 Session.prototype._handle_start_success = function (data, status, xhr) {
91 Session.prototype._handle_start_success = function (data, status, xhr) {
88 this.id = data.id;
92 this.id = data.id;
89 var kernel_service_url = utils.url_path_join(this.base_url, "api/kernels");
93 var kernel_service_url = utils.url_path_join(this.base_url, "api/kernels");
90 this.kernel = new kernel.Kernel(kernel_service_url, this.notebook);
94 this.kernel = new kernel.Kernel(kernel_service_url, this.notebook, this.kernel_name);
91 this.kernel._kernel_started(data.kernel);
95 this.kernel._kernel_started(data.kernel);
92 };
96 };
93
97
@@ -80,7 +80,7 b' casper.notebook_test(function () {'
80 });
80 });
81 return return_this_thing;
81 return return_this_thing;
82 }, {nbname:nbname});
82 }, {nbname:nbname});
83 this.test.assertEquals(notebook_url == null, false, "Escaped URL in notebook list");
83 this.test.assertNotEquals(notebook_url, null, "Escaped URL in notebook list");
84 // open the notebook
84 // open the notebook
85 this.open(notebook_url);
85 this.open(notebook_url);
86 });
86 });
@@ -63,7 +63,7 b' casper.kernel_running = function() {'
63 casper.shutdown_current_kernel = function () {
63 casper.shutdown_current_kernel = function () {
64 // Shut down the current notebook's kernel.
64 // Shut down the current notebook's kernel.
65 this.thenEvaluate(function() {
65 this.thenEvaluate(function() {
66 IPython.notebook.kernel.kill();
66 IPython.notebook.session.delete();
67 });
67 });
68 // We close the page right after this so we need to give it time to complete.
68 // We close the page right after this so we need to give it time to complete.
69 this.wait(1000);
69 this.wait(1000);
@@ -92,7 +92,7 b' class MultiKernelManager(LoggingConfigurable):'
92 def __contains__(self, kernel_id):
92 def __contains__(self, kernel_id):
93 return kernel_id in self._kernels
93 return kernel_id in self._kernels
94
94
95 def start_kernel(self, **kwargs):
95 def start_kernel(self, kernel_name='python', **kwargs):
96 """Start a new kernel.
96 """Start a new kernel.
97
97
98 The caller can pick a kernel_id by passing one in as a keyword arg,
98 The caller can pick a kernel_id by passing one in as a keyword arg,
@@ -111,7 +111,7 b' class MultiKernelManager(LoggingConfigurable):'
111 # including things like its transport and ip.
111 # including things like its transport and ip.
112 km = self.kernel_manager_factory(connection_file=os.path.join(
112 km = self.kernel_manager_factory(connection_file=os.path.join(
113 self.connection_dir, "kernel-%s.json" % kernel_id),
113 self.connection_dir, "kernel-%s.json" % kernel_id),
114 parent=self, autorestart=True, log=self.log
114 parent=self, autorestart=True, log=self.log, kernel_name=kernel_name,
115 )
115 )
116 km.start_kernel(**kwargs)
116 km.start_kernel(**kwargs)
117 self._kernels[kernel_id] = km
117 self._kernels[kernel_id] = km
General Comments 0
You need to be logged in to leave comments. Login now