-
Notifications
You must be signed in to change notification settings - Fork 131
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Fix to make IPerl notebooks running in notebook-http mode #271
Conversation
I'm not familiar with One approach would be to add a sibling property on Since it doesn't appear Please make the additional parameter optional since I don't think language is required in I hope that helps. |
@kevin-bates Thanks for your reply in detail and it's a great help to me. 👍 I agree that My current change is like an instant hack, I'll make a refactoring of it. |
Thanks for the updates @gingerhot. These changes look fine to me. The py 2.7 failure appears to be related to a timeout and not the changes - as best as I can tell. |
@kevin-bates Thanks for your reply. And yes, I search the codes for I checked py 2.7 failure and also think maybe not a problem of my commit as local |
"""Creates an assignment statement of bundle JSON-encoded to a variable | ||
named `REQUEST`. | ||
named `REQUEST` by default or kernel_language specific. | ||
|
||
Returns | ||
------- | ||
str | ||
`REQUEST = "<json-encoded expression>"` |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This line of the doc string is no longer accurate after the change, right?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it also accurate, too. It'll keep the variable as REQUEST
for those languages works well and a similar variable name for those kernel_language specific ones. I think the description is consistent to following codes logically.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Line 22 says that REQUEST =
is returned, unconditionally.
Line 17 says that the return value can be different, depending on the kernel language.
That's a contradiction.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, Line 22 should be updated.
@@ -122,7 +122,8 @@ def create_request_handlers(self): | |||
handler_args = { 'sources' : verb_source_map, | |||
'response_sources' : response_source_map, | |||
'kernel_pool' : self.kernel_pool, | |||
'kernel_name' : self.parent.kernel_manager.seed_kernelspec | |||
'kernel_name' : self.parent.kernel_manager.seed_kernelspec, | |||
'kernel_language' : getattr(self.parent.kernel_spec_manager.get_kernel_spec(self.parent.kernel_manager.seed_kernelspec), 'language', 'no_spec') |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not sure that this is a good place for the lookup. Can't the handler do the lookup itself?
If there is a need to set kernel_language from outside in some cases, then give it a default of null or the empty string, and let the handler deal with that. If there is no need to set kernel_language from outside, then don't add it to the handler_args at all.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it as same as other args in handler_args, that's why we construct a handler_args
here, we just pass the args what we need instead of a some object and then get just a needed attribute from it.
And I read through the code once more and find that we use the lang
extracted from notebook's metadata to determine the comment sign:
https://github.com/jupyter/kernel_gateway/blob/05e714805e5e74e1b4dbcbe463e4ab8ac295c490/kernel_gateway/notebook_http/__init__.py#L65-L69
So I think maybe we should also use this same lang
to keep them consistent. And here we can make lang
as an instance variable.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The difference to the other args is that kernel_language
is dependent on kernel_name
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I ever thought that kernel_language
is dependent on kernel_name
, but now I don't think so. Since I found that we can get the language
directly like the above mentioned:
And I think we should keep it consistent, i.e. get the language
from the same source, the notebook's metadata.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Oh, I see. That's one of the cases where I was missing the big picture :-)
Yes, the common source of information is the notebook, not the kernel_name.
Then it makes sense to pass both values as separate arguments.
@@ -35,6 +35,8 @@ class NotebookAPIHandler(TokenAuthorizationMixin, | |||
kernel_name | |||
Kernel spec name used to launch the kernel pool. Identifies the | |||
language of the source code cells. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If kernel_language is added, the second sentence in the description of kernel_name is no longer accurate.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, if kernel_language
is decided to be added, then this description should be updated.
@@ -45,11 +47,12 @@ class NotebookAPIHandler(TokenAuthorizationMixin, | |||
services.cell.parser.APICellParser for detail about how the source cells | |||
are identified, parsed, and associated with HTTP verbs and paths. | |||
""" | |||
def initialize(self, sources, response_sources, kernel_pool, kernel_name): | |||
def initialize(self, sources, response_sources, kernel_pool, kernel_name, kernel_language='no_spec'): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why are you using a magic value 'no_spec' as the default, instead of null or an empty string? I don't see a check for this magic value in your changes. If this "language" has now a special meaning, it would have to be documented somewhere.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I intended to add it as a self-explanatory value, or maybe there's a need of checking on it in further development. I think an empty string is ok, too.
@@ -12,17 +12,20 @@ | |||
APPLICATION_JSON = 'application/json' | |||
TEXT_PLAIN = 'text/plain' | |||
|
|||
def format_request(bundle): | |||
def format_request(bundle, kernel_language='no_spec'): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Another instance of the magic value 'no_spec'. I've expressed my concerns about this in one of the other review comments.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
same as above.
Hello @gingerhot, thanks for your contribution! I've reviewed the code changes by just looking at the diff. If some of my comments are invalid in the greater context, feel free to argue against :-) Could you please add a little unit test for the new behavior you've introduced? That would be great. Regarding |
@rolweber thanks for your review and reply, and I see and I will :-) And I'll add some unit tests in further commits. Do you mean keep the |
@gingerhot: Great! Yes, I suggest to keep the kernel_name as an argument and do the language lookup in the handler. |
@rolweber As I replied above that I think the |
…d argument of format_request
@rolweber I make a refactoring based on our discussions and add two unit tests. |
def test_format_request_with_a_kernel_language_arg(self): | ||
test_request = ('''{"body": "", "headers": {}, "args": {}, "path": {}}''') | ||
request_code = format_request(test_request, 'perl') | ||
self.assertTrue(request_code.startswith("my $REQUEST"), "Call format_request with a kernel language argument was not formatted correctly") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks. Would you mind adding two more of these tests, with languages 'python' and 'scala'? Python is kind of a default language, and I've seen special treatment of Scala for the comment_prefix.
These unit tests cover the changes in format_request. I would feel safer if we also had unit tests that cover the creation of the handler, where you added the new argument.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'll add the more languages unit tests to format_request.
But for the creation of the handler I didn't find any existed tests for it ... maybe we could add them later?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm still not happy about the default 'no_spec'
being used in several places, but that might just be a personal preference.
Nevertheless, I think this change is mature enough to be merged.
@gingerhot: I have approved this PR as it is, but I'd rather wait for @parente or some other committer to have a final look. As you can see from my comments, I still have small concerns and would like someone else to decide whether these are relevant or not. I'm not firm enough in Python and this codebase to impose my gut feeling on your contribution :-) |
@rolweber About |
My idea is to use either |
I think empty string |
@gingerhot: Thanks for putting so much effort into this! |
@rolweber My pleasure~ and thank you for your patience. |
When I try the notebook-http mode with the IPerl kernel and run into a constant variable assignment problem.
In Perl when we use a all-uppercase name like
REQUEST
, it means the variable is a constant. An assignment likeREQUEST = ...
is illegal, i.e. we can't use a "=" to assign a value to a constant variable.And in fact in Ruby the uppercase name is treated as a constant, too. But in Ruby the syntax
REQUEST = ...
is a valid assignment, it seems there's no problem with Ruby. And nor do Python.So here I add a kernel dependent change to the
request_format
function. When the kernel isiperl
, it takes$REQUEST
as a variable that could be assigned a value with=
. And the way may be useful for some other kernels in such a situation.And I test it with a IPerl notebook and it works.