boot
This commit is contained in:
@@ -1,17 +1,9 @@
|
||||
set (EXTRAS
|
||||
MANIFEST.in
|
||||
YAP_KERNEL.md
|
||||
)
|
||||
|
||||
set (PL_SOURCES
|
||||
yap_ipython/prolog/jupyter.yap
|
||||
)
|
||||
|
||||
set (PYTHON_SOURCES
|
||||
yap_ipython/core/getipython.py
|
||||
yap_ipython/core/__init__.py
|
||||
yap_ipython/core/interactiveshell.py
|
||||
yap_ipython/core/modulefind.py
|
||||
# yap_ipython/core/modulefind.py
|
||||
yap_ipython/core/oinspect.py
|
||||
yap_ipython/core/release.py
|
||||
yap_ipython/core/shellapp.py
|
||||
@@ -59,19 +51,62 @@
|
||||
yap_kernel/pylab/config.py
|
||||
)
|
||||
|
||||
configure_file(setup.py.in ${CMAKE_CURRENT_BINARY_DIR}/setup.py)
|
||||
configure_file(${CMAKE_SOURCE_DIR}/misc/editors/prolog.js.in ${CMAKE_CURRENT_BINARY_DIR}/prolog.js )
|
||||
set (EXTRAS
|
||||
MANIFEST.in
|
||||
YAP_KERNEL.md
|
||||
setup.py
|
||||
setup.cfg
|
||||
README.md
|
||||
)
|
||||
|
||||
set (RESOURCES
|
||||
resources/custom.js
|
||||
resources/prolog.js
|
||||
#resources/logo-32x32.png
|
||||
#resources/logo-64x64.png
|
||||
)
|
||||
set (RENAMED_RESOURCES
|
||||
resources/logo-32x32.png
|
||||
resources/logo-64x64.png
|
||||
# resources/codemirror/mode/prolog/prolog.js
|
||||
)
|
||||
|
||||
set (PL_SOURCES
|
||||
yap_ipython/prolog/jupyter.yap
|
||||
)
|
||||
|
||||
set(FILES ${PYTHON_SOURCES} ${PL_SOURCES} ${EXTRAS} ${RESOURCES})
|
||||
|
||||
set(SETUP_PY ${CMAKE_CURRENT_BINARY_DIR}/setup.py)
|
||||
|
||||
add_custom_target( YAPKernel ALL
|
||||
add_custom_command(OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/${i}
|
||||
COMMAND ${CMAKE_COMMAND} -E tar cvf ${CMAKE_CURRENT_BINARY_DIR}/yap.tgz ${FILESi}
|
||||
|
||||
|
||||
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
|
||||
)
|
||||
|
||||
|
||||
add_custom_command(OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/resources/logo-32x32.png
|
||||
COMMAND ${CMAKE_COMMAND} -E tar xvf yap.tgz
|
||||
COMMAND ${CMAKE_COMMAND} -E copy_if_changed ${CMAKE_SOURCE_DIR}/docs/icons/yap_32z32x32.png ${CMAKE_CURRENT_BINARY_DIR}/resources/logo-32x32.png
|
||||
DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/docs/icons/yap_32x32x32.png
|
||||
)
|
||||
|
||||
|
||||
add_custom_command(OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/resources/logo-64x64.png
|
||||
COMMAND ${CMAKE_COMMAND} -E copy_if_changed ${CMAKE_SOURCE_DIR}/docs/icons/yap_64x64x32.png ${CMAKE_CURRENT_BINARY_DIR}/resources/logo-64x64.png
|
||||
)
|
||||
|
||||
add_custom_target(YAP_KERNEL
|
||||
COMMAND ${CMAKE_COMMAND} -E tar xvf yap.tgz
|
||||
COMMAND ${PYTHON_EXECUTABLE} ${SETUP_PY} build sdist bdist
|
||||
WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}
|
||||
DEPENDS YAP4PY
|
||||
)
|
||||
)
|
||||
|
||||
|
||||
install(CODE "execute_process(COMMAND ${PYTHON_EXECUTABLE} -m pip install --ignore-installed --no-deps .
|
||||
COMMAND ${PYTHON_EXECUTABLE} -m yap_kernel.kernelspec
|
||||
WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR})")
|
||||
|
||||
install(FILES ${PL_SOURCES} DESTINATION ${libpl} )
|
||||
|
@@ -1,9 +1,42 @@
|
||||
/*define(['./prolog.js'], function(){
|
||||
|
||||
var onload = function(){
|
||||
console.log("I am being loaded");
|
||||
;(function(window_CodeMirror){
|
||||
"use strict";
|
||||
|
||||
|
||||
};
|
||||
return {onload:onload}
|
||||
});*/
|
||||
// the `require` namespace for codemirror
|
||||
CM_PATH = "components/codemirror/";
|
||||
|
||||
define(
|
||||
[
|
||||
"underscore",
|
||||
"jquery",
|
||||
CM_PATH + "lib/codemirror",
|
||||
"base/js/namespace",
|
||||
// silent upgrades
|
||||
"./jshint.js",
|
||||
CM_PATH + "addon/lint/javascript-lint",
|
||||
CM_PATH + "addon/hint/javascript-hint",
|
||||
CM_PATH + "addon/lint/lint",
|
||||
CM_PATH + "addon/hint/show-hint",
|
||||
"./prolog.js"
|
||||
],
|
||||
function(_, $, CodeMirror, Jupyter){
|
||||
|
||||
// the main function
|
||||
cm_tweak_js = function(cell){
|
||||
var editor = cell.code_mirror,
|
||||
opts = {},
|
||||
meta = ensure_ns(cell),
|
||||
keys = editor.getOption("extraKeys") || {},
|
||||
mode = editor.getMode();
|
||||
|
||||
// only update editors we care about, reset ones we might have messed
|
||||
if(!editor){
|
||||
return;
|
||||
} else {
|
||||
editor.setOption("mode", "x-text/prolog");
|
||||
}
|
||||
}
|
||||
}
|
||||
} // the `define` callback
|
||||
); // the `define`
|
||||
).call(this, window.CodeMirror);
|
||||
|
@@ -39,20 +39,19 @@ pjoin = os.path.join
|
||||
here = os.path.abspath(os.path.dirname(__file__))
|
||||
# pkg_root = pjoin(here, name)
|
||||
|
||||
packages = setuptools.find_packages('${CMAKE_CURRENT_SOURCE_DIR}')
|
||||
packages = setuptools.find_packages(here)
|
||||
# for d, _, _ in os.walk(pjoin(here, name)):
|
||||
# if os.path.exists(pjoin(d, '__init__.py')):
|
||||
# packages.append(d[len(here)+1:].replace(os.path.sep, '.'))
|
||||
|
||||
sys.path.insert(0, "${CMAKE_CURRENT_SOURCE_DIR}")
|
||||
sys.path.insert(0, here)
|
||||
package_data = {
|
||||
'yap_ipython': ['prolog/*.*'],
|
||||
'yap_kernel': ['resources/*.*']
|
||||
}
|
||||
|
||||
|
||||
version_ns = {}
|
||||
with open(pjoin('${CMAKE_CURRENT_SOURCE_DIR}', name, '_version.py')) as f:
|
||||
version_ns = {here, name, '_version.py')) as f:
|
||||
exec(f.read(), {}, version_ns)
|
||||
|
||||
|
||||
@@ -65,7 +64,7 @@ setup_args = dict(
|
||||
packages = packages,
|
||||
py_modules = ['yap_kernel_launcher'],
|
||||
package_data = package_data,
|
||||
package_dir = {'':"${CMAKE_CURRENT_SOURCE_DIR}"},
|
||||
package_dir = {'':here},
|
||||
description = "YAP Kernel for Jupyter",
|
||||
author = 'YAP Development Team',
|
||||
author_email = 'YAP-dev@scipy.org',
|
||||
@@ -95,29 +94,24 @@ if any(a.startswith(('bdist', 'build', 'install')) for a in sys.argv):
|
||||
from yap_kernel.kernelspec import write_kernel_spec, make_yap_kernel_cmd, KERNEL_NAME
|
||||
|
||||
|
||||
argv = make_yap_kernel_cmd(executable='python')
|
||||
argv = make_yap_kernel_cmd(executable=sys.executable)
|
||||
dest = os.path.join(here, 'resources')
|
||||
try:
|
||||
shutil.rmtree(dest)
|
||||
os.makedirs( dest )
|
||||
shutil.copy2('${CMAKE_SOURCE_DIR}/docs/icons/yap_32x32x32.png',pjoin(dest,"logo_32x32.png"))
|
||||
shutil.copy2('${CMAKE_SOURCE_DIR}/docs/icons/yap_64x64x32.png',pjoin(dest,"logo_64x64.png"))
|
||||
write_kernel_spec(dest, overrides={'argv': argv})
|
||||
except:
|
||||
pass
|
||||
# shutil.copy('${CMAKE_CURRENT_SOURCE_DIR}/kernel.js',dest)
|
||||
# shutil.copy('${CMAKE_SOURCE_DIR}/misc/editors/prolog.js',dest)
|
||||
setup_args['data_files'] = [(pjoin('share', 'jupyter', 'kernels', KERNEL_NAME), glob(pjoin(dest, '*')))]
|
||||
#setup_args['data_files'] = [(pjoin('share', 'jupyter', 'kernels', KERNEL_NAME), glob(pjoin(dest, '*')))]
|
||||
mode_loc = pjoin( sysconfig.get_path('platlib'), 'notebook', 'static', 'components', 'codemirror', 'mode', 'prolog')
|
||||
custom_loc = pjoin( sysconfig.get_path('platlib'), 'notebook', 'static', 'custom')
|
||||
# try:
|
||||
# shutil.copy( pjoin( custom_loc, "custom.js") , pjoin( custom_loc, "custom.js.orig"))
|
||||
# shutil.copy( "${CMAKE_CURRENT_SOURCE_DIR}/custom.js" , pjoin( custom_loc, "custom.js"))
|
||||
# if not os.path.exists(mode_loc):
|
||||
# os.makedirs(mode_loc)
|
||||
# shutil.copy( "${CMAKE_SOURCE_DIR}/misc/editors/prolog.js" , mode_loc)
|
||||
# except:
|
||||
# pass
|
||||
try:
|
||||
shutil.copy( pjoin( custom_loc, "custom.js") , pjoin( custom_loc, "custom.js.orig"))
|
||||
shutil.copy( pjoin( "resources", "custom.js") , pjoin( custom_loc, "custom.js"))
|
||||
if not os.path.exists(mode_loc):
|
||||
os.makedirs(mode_loc)
|
||||
shutil.copy( pjoin( "resources","prolog.js") , mode_loc)
|
||||
except:
|
||||
pass
|
||||
|
||||
extras_require = setuptools_args['extras_require'] = {
|
||||
'test:python_version=="2.7"': ['mock'],
|
@@ -74,7 +74,7 @@ manager.
|
||||
You will find that the following are experimental:
|
||||
|
||||
- :any:`provisionalcompleter`
|
||||
- :any:`IPCompleter.completions`
|
||||
- :any:PyCompleter.completions`
|
||||
- :any:`Completion`
|
||||
- :any:`rectify_completions`
|
||||
|
||||
@@ -154,7 +154,7 @@ except ImportError:
|
||||
#-----------------------------------------------------------------------------
|
||||
|
||||
# Public API
|
||||
__all__ = ['Completer','IPCompleter']
|
||||
__all__ = ['Completer','YAPCompleter']
|
||||
|
||||
if sys.platform == 'win32':
|
||||
PROTECTABLES = ' '
|
||||
@@ -349,7 +349,7 @@ class Completion:
|
||||
Completion object used and return by yap_ipython completers.
|
||||
|
||||
.. warning:: Unstable
|
||||
|
||||
|
||||
This function is unstable, API may change without warning.
|
||||
It will also raise unless use in proper context manager.
|
||||
|
||||
@@ -590,7 +590,7 @@ class Completer(Configurable):
|
||||
'information for experimental jedi integration.')\
|
||||
.tag(config=True)
|
||||
|
||||
backslash_combining_completions = Bool(True,
|
||||
backslash_combining_completions = Bool(True,
|
||||
help="Enable unicode completions, e.g. \\alpha<tab> . "
|
||||
"Includes completion of latex commands, unicode names, and expanding "
|
||||
"unicode characters back to latex commands.").tag(config=True)
|
||||
@@ -692,7 +692,7 @@ class Completer(Configurable):
|
||||
|
||||
# Another option, seems to work great. Catches things like ''.<tab>
|
||||
m = re.match(r"(\S+(\.\w+)*)\.(\w*)$", text)
|
||||
|
||||
|
||||
if m:
|
||||
expr, attr = m.group(1, 3)
|
||||
elif self.greedy:
|
||||
@@ -702,7 +702,7 @@ class Completer(Configurable):
|
||||
expr, attr = m2.group(1,2)
|
||||
else:
|
||||
return []
|
||||
|
||||
|
||||
try:
|
||||
obj = eval(expr, self.namespace)
|
||||
except:
|
||||
@@ -737,7 +737,7 @@ def get__all__entries(obj):
|
||||
words = getattr(obj, '__all__')
|
||||
except:
|
||||
return []
|
||||
|
||||
|
||||
return [w for w in words if isinstance(w, str)]
|
||||
|
||||
|
||||
@@ -886,14 +886,14 @@ def _safe_isinstance(obj, module, class_name):
|
||||
|
||||
def back_unicode_name_matches(text):
|
||||
u"""Match unicode characters back to unicode name
|
||||
|
||||
|
||||
This does ``☃`` -> ``\\snowman``
|
||||
|
||||
Note that snowman is not a valid python3 combining character but will be expanded.
|
||||
Though it will not recombine back to the snowman character by the completion machinery.
|
||||
|
||||
This will not either back-complete standard sequences like \\n, \\b ...
|
||||
|
||||
|
||||
Used on Python 3 only.
|
||||
"""
|
||||
if len(text)<2:
|
||||
@@ -916,7 +916,7 @@ def back_unicode_name_matches(text):
|
||||
|
||||
def back_latex_name_matches(text:str):
|
||||
"""Match latex characters back to unicode name
|
||||
|
||||
|
||||
This does ``\\ℵ`` -> ``\\aleph``
|
||||
|
||||
Used on Python 3 only.
|
||||
@@ -990,7 +990,7 @@ def _make_signature(completion)-> str:
|
||||
|
||||
class IPCompleter(Completer):
|
||||
"""Extension of the completer class with yap_ipython-specific features"""
|
||||
|
||||
|
||||
@observe('greedy')
|
||||
def _greedy_changed(self, change):
|
||||
"""update the splitter and readline delims when greedy is changed"""
|
||||
@@ -998,36 +998,36 @@ class IPCompleter(Completer):
|
||||
self.splitter.delims = GREEDY_DELIMS
|
||||
else:
|
||||
self.splitter.delims = DELIMS
|
||||
|
||||
|
||||
merge_completions = Bool(True,
|
||||
help="""Whether to merge completion results into a single list
|
||||
|
||||
|
||||
If False, only the completion results from the first non-empty
|
||||
completer will be returned.
|
||||
"""
|
||||
).tag(config=True)
|
||||
omit__names = Enum((0,1,2), default_value=2,
|
||||
help="""Instruct the completer to omit private method names
|
||||
|
||||
|
||||
Specifically, when completing on ``object.<tab>``.
|
||||
|
||||
|
||||
When 2 [default]: all names that start with '_' will be excluded.
|
||||
|
||||
|
||||
When 1: all 'magic' names (``__foo__``) will be excluded.
|
||||
|
||||
|
||||
When 0: nothing will be excluded.
|
||||
"""
|
||||
).tag(config=True)
|
||||
limit_to__all__ = Bool(False,
|
||||
help="""
|
||||
DEPRECATED as of version 5.0.
|
||||
|
||||
|
||||
Instruct the completer to use __all__ for the completion
|
||||
|
||||
|
||||
Specifically, when completing on ``object.<tab>``.
|
||||
|
||||
|
||||
When True: only those names in obj.__all__ will be included.
|
||||
|
||||
|
||||
When False [default]: the __all__ attribute is ignored
|
||||
""",
|
||||
).tag(config=True)
|
||||
@@ -1060,7 +1060,7 @@ class IPCompleter(Completer):
|
||||
secondary optional dict for completions, to
|
||||
handle cases (such as yap_ipython embedded inside functions) where
|
||||
both Python scopes are visible.
|
||||
|
||||
|
||||
use_readline : bool, optional
|
||||
DEPRECATED, ignored since yap_ipython 6.0, will have no effects
|
||||
"""
|
||||
@@ -1611,7 +1611,7 @@ class IPCompleter(Completer):
|
||||
closing_quote, token_offset, matches = match_dict_keys(keys, prefix, self.splitter.delims)
|
||||
if not matches:
|
||||
return matches
|
||||
|
||||
|
||||
# get the cursor position of
|
||||
# - the text being completed
|
||||
# - the start of the key text
|
||||
@@ -1622,13 +1622,13 @@ class IPCompleter(Completer):
|
||||
completion_start = key_start + token_offset
|
||||
else:
|
||||
key_start = completion_start = match.end()
|
||||
|
||||
|
||||
# grab the leading prefix, to make sure all completions start with `text`
|
||||
if text_start > key_start:
|
||||
leading = ''
|
||||
else:
|
||||
leading = text[text_start:completion_start]
|
||||
|
||||
|
||||
# the index of the `[` character
|
||||
bracket_idx = match.end(1)
|
||||
|
||||
@@ -1647,18 +1647,18 @@ class IPCompleter(Completer):
|
||||
# brackets were opened inside text, maybe close them
|
||||
if not continuation.startswith(']'):
|
||||
suf += ']'
|
||||
|
||||
|
||||
return [leading + k + suf for k in matches]
|
||||
|
||||
def unicode_name_matches(self, text):
|
||||
u"""Match Latex-like syntax for unicode characters base
|
||||
on the name of the character.
|
||||
|
||||
|
||||
This does ``\\GREEK SMALL LETTER ETA`` -> ``η``
|
||||
|
||||
Works only on valid python 3 identifier, or on combining characters that
|
||||
will combine to form a valid identifier.
|
||||
|
||||
|
||||
Used on Python 3 only.
|
||||
"""
|
||||
slashpos = text.rfind('\\')
|
||||
@@ -1676,7 +1676,7 @@ class IPCompleter(Completer):
|
||||
|
||||
def latex_matches(self, text):
|
||||
u"""Match Latex syntax for unicode characters.
|
||||
|
||||
|
||||
This does both ``\\alp`` -> ``\\alpha`` and ``\\alpha`` -> ``α``
|
||||
|
||||
Used on Python 3 only.
|
||||
@@ -1748,13 +1748,13 @@ class IPCompleter(Completer):
|
||||
Returns an iterator over the possible completions
|
||||
|
||||
.. warning:: Unstable
|
||||
|
||||
|
||||
This function is unstable, API may change without warning.
|
||||
It will also raise unless use in proper context manager.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
|
||||
|
||||
text:str
|
||||
Full text of the current input, multi line string.
|
||||
offset:int
|
||||
@@ -1783,7 +1783,7 @@ class IPCompleter(Completer):
|
||||
and usual yap_ipython completion.
|
||||
|
||||
.. note::
|
||||
|
||||
|
||||
Completions are not completely deduplicated yet. If identical
|
||||
completions are coming from different sources this function does not
|
||||
ensure that each completion object will only be present once.
|
||||
@@ -1973,7 +1973,7 @@ class IPCompleter(Completer):
|
||||
if name_text:
|
||||
return name_text, name_matches[:MATCHES_LIMIT], \
|
||||
[meth.__qualname__]*min(len(name_matches), MATCHES_LIMIT), ()
|
||||
|
||||
|
||||
|
||||
# If no line buffer is given, assume the input text is all there was
|
||||
if line_buffer is None:
|
||||
|
@@ -292,7 +292,7 @@ class InputSplitter(object):
|
||||
"""
|
||||
# A cache for storing the current indentation
|
||||
# The first value stores the most recently processed source input
|
||||
# The second value is the number of spaces for the current indentation
|
||||
# The second value is the number of spaces for the current indentation
|
||||
# If self.source matches the first value, the second value is a valid
|
||||
# current indentation. Otherwise, the cache is invalid and the indentation
|
||||
# must be recalculated.
|
||||
@@ -345,14 +345,14 @@ class InputSplitter(object):
|
||||
|
||||
def check_complete(self, source):
|
||||
"""Return whether a block of code is ready to execute, or should be continued
|
||||
|
||||
|
||||
This is a non-stateful API, and will reset the state of this InputSplitter.
|
||||
|
||||
|
||||
Parameters
|
||||
----------
|
||||
source : string
|
||||
Python input code, which can be multiline.
|
||||
|
||||
|
||||
Returns
|
||||
-------
|
||||
status : str
|
||||
@@ -441,7 +441,7 @@ class InputSplitter(object):
|
||||
guess whether a block is complete or not based solely on prior and
|
||||
current input lines. The InputSplitter considers it has a complete
|
||||
interactive block and will not accept more input when either:
|
||||
|
||||
|
||||
* A SyntaxError is raised
|
||||
|
||||
* The code is complete and consists of a single line or a single
|
||||
@@ -461,20 +461,20 @@ class InputSplitter(object):
|
||||
if not self._is_complete:
|
||||
#print("Not complete") # debug
|
||||
return True
|
||||
|
||||
|
||||
# The user can make any (complete) input execute by leaving a blank line
|
||||
last_line = self.source.splitlines()[-1]
|
||||
if (not last_line) or last_line.isspace():
|
||||
#print("Blank line") # debug
|
||||
return False
|
||||
|
||||
|
||||
# If there's just a single line or AST node, and we're flush left, as is
|
||||
# the case after a simple statement such as 'a=1', we want to execute it
|
||||
# straight away.
|
||||
if self.get_indent_spaces() == 0:
|
||||
if len(self.source.splitlines()) <= 1:
|
||||
return False
|
||||
|
||||
|
||||
try:
|
||||
code_ast = ast.parse(u''.join(self._buffer))
|
||||
except Exception:
|
||||
@@ -528,11 +528,11 @@ class IPythonInputSplitter(InputSplitter):
|
||||
|
||||
# String with raw, untransformed input.
|
||||
source_raw = ''
|
||||
|
||||
|
||||
# Flag to track when a transformer has stored input that it hasn't given
|
||||
# back yet.
|
||||
transformer_accumulating = False
|
||||
|
||||
|
||||
# Flag to track when assemble_python_lines has stored input that it hasn't
|
||||
# given back yet.
|
||||
within_python_line = False
|
||||
@@ -547,7 +547,7 @@ class IPythonInputSplitter(InputSplitter):
|
||||
super(IPythonInputSplitter, self).__init__()
|
||||
self._buffer_raw = []
|
||||
self._validate = True
|
||||
|
||||
|
||||
if physical_line_transforms is not None:
|
||||
self.physical_line_transforms = physical_line_transforms
|
||||
else:
|
||||
@@ -557,7 +557,7 @@ class IPythonInputSplitter(InputSplitter):
|
||||
ipy_prompt(),
|
||||
cellmagic(end_on_blank_line=line_input_checker),
|
||||
]
|
||||
|
||||
|
||||
self.assemble_logical_lines = assemble_logical_lines()
|
||||
if logical_line_transforms is not None:
|
||||
self.logical_line_transforms = logical_line_transforms
|
||||
@@ -568,21 +568,21 @@ class IPythonInputSplitter(InputSplitter):
|
||||
assign_from_magic(),
|
||||
assign_from_system(),
|
||||
]
|
||||
|
||||
|
||||
self.assemble_python_lines = assemble_python_lines()
|
||||
if python_line_transforms is not None:
|
||||
self.python_line_transforms = python_line_transforms
|
||||
else:
|
||||
# We don't use any of these at present
|
||||
self.python_line_transforms = []
|
||||
|
||||
|
||||
@property
|
||||
def transforms(self):
|
||||
"Quick access to all transformers."
|
||||
return self.physical_line_transforms + \
|
||||
[self.assemble_logical_lines] + self.logical_line_transforms + \
|
||||
[self.assemble_python_lines] + self.python_line_transforms
|
||||
|
||||
|
||||
@property
|
||||
def transforms_in_use(self):
|
||||
"""Transformers, excluding logical line transformers if we're in a
|
||||
@@ -607,13 +607,13 @@ class IPythonInputSplitter(InputSplitter):
|
||||
# Nothing that calls reset() expects to handle transformer
|
||||
# errors
|
||||
pass
|
||||
|
||||
|
||||
def flush_transformers(self):
|
||||
def _flush(transform, outs):
|
||||
"""yield transformed lines
|
||||
|
||||
|
||||
always strings, never None
|
||||
|
||||
|
||||
transform: the current transform
|
||||
outs: an iterable of previously transformed inputs.
|
||||
Each may be multiline, which will be passed
|
||||
@@ -625,16 +625,16 @@ class IPythonInputSplitter(InputSplitter):
|
||||
tmp = transform.push(line)
|
||||
if tmp is not None:
|
||||
yield tmp
|
||||
|
||||
|
||||
# reset the transform
|
||||
tmp = transform.reset()
|
||||
if tmp is not None:
|
||||
yield tmp
|
||||
|
||||
|
||||
out = []
|
||||
for t in self.transforms_in_use:
|
||||
out = _flush(t, out)
|
||||
|
||||
|
||||
out = list(out)
|
||||
if out:
|
||||
self._store('\n'.join(out))
|
||||
@@ -645,7 +645,7 @@ class IPythonInputSplitter(InputSplitter):
|
||||
out = self.source_raw
|
||||
self.reset()
|
||||
return out
|
||||
|
||||
|
||||
def source_reset(self):
|
||||
try:
|
||||
self.flush_transformers()
|
||||
@@ -714,18 +714,14 @@ class IPythonInputSplitter(InputSplitter):
|
||||
|
||||
if transformed_lines_list:
|
||||
transformed_lines = '\n'.join(transformed_lines_list)
|
||||
return super(IPythonInputSplitter, self).push(transformed_lines)
|
||||
else:
|
||||
# Got nothing back from transformers - they must be waiting for
|
||||
# more input.
|
||||
return False
|
||||
return hasSyntaxError(self, lines)
|
||||
|
||||
def _transform_line(self, line):
|
||||
"""Push a line of input code through the various transformers.
|
||||
|
||||
|
||||
Returns any output from the transformers, or None if a transformer
|
||||
is accumulating lines.
|
||||
|
||||
|
||||
Sets self.transformer_accumulating as a side effect.
|
||||
"""
|
||||
def _accumulating(dbg):
|
||||
@@ -738,24 +734,8 @@ class IPythonInputSplitter(InputSplitter):
|
||||
if line is None:
|
||||
return _accumulating(transformer)
|
||||
|
||||
if not self.within_python_line:
|
||||
line = self.assemble_logical_lines.push(line)
|
||||
if line is None:
|
||||
return _accumulating('acc logical line')
|
||||
|
||||
for transformer in self.logical_line_transforms:
|
||||
line = transformer.push(line)
|
||||
if line is None:
|
||||
return _accumulating(transformer)
|
||||
|
||||
line = self.assemble_python_lines.push(line)
|
||||
if line is None:
|
||||
self.within_python_line = True
|
||||
return _accumulating('acc python line')
|
||||
else:
|
||||
self.within_python_line = False
|
||||
|
||||
for transformer in self.python_line_transforms:
|
||||
for transformer in self.logical_line_transforms:
|
||||
line = transformer.push(line)
|
||||
if line is None:
|
||||
return _accumulating(transformer)
|
||||
@@ -763,4 +743,3 @@ class IPythonInputSplitter(InputSplitter):
|
||||
#print("transformers clear") #debug
|
||||
self.transformer_accumulating = False
|
||||
return line
|
||||
|
||||
|
@@ -29,6 +29,7 @@ from io import open as io_open
|
||||
|
||||
from pickleshare import PickleShareDB
|
||||
|
||||
import yap_ipython.yapi
|
||||
from traitlets.config.configurable import SingletonConfigurable
|
||||
from yap_ipython.core import oinspect
|
||||
from yap_ipython.core import magic
|
||||
@@ -78,7 +79,7 @@ from traitlets import (
|
||||
from warnings import warn
|
||||
from logging import error
|
||||
import yap_ipython.core.hooks
|
||||
from yap_ipython.yapi import YAPRun, YAPCompleter
|
||||
from yap_ipython.yapi import YAPRun, YAPCompleter, YAPInputSplitter
|
||||
|
||||
from typing import List as ListType
|
||||
from ast import AST
|
||||
@@ -337,15 +338,17 @@ class InteractiveShell(SingletonConfigurable):
|
||||
|
||||
# Input splitter, to transform input line by line and detect when a block
|
||||
# is ready to be executed.
|
||||
input_splitter = Instance('yap_ipython.core.inputsplitter.IPythonInputSplitter',
|
||||
(), {'line_input_checker': True})
|
||||
#input_splitter = Instance('yap_ipython.core.inputsplitter.IPythonInputSplitter',
|
||||
# (), {'line_input_checker': True})
|
||||
input_splitter = Instance('yap_ipython.yapi.YAPInputSplitter',
|
||||
(), {'line_input_checker': False})
|
||||
|
||||
# This InputSplitter instance is used to transform completed cells before
|
||||
# running them. It allows cell magics to contain blank lines.
|
||||
# input_transformer_manager = Instance('yap_ipython.core.inputsplitter.IPythonInputSplitter',
|
||||
# (), {'line_input_checker': False})
|
||||
input_transformer_manager = Instance('yap_ipython.yapi.YAPLineProcessor',
|
||||
(), {'line_input_checker': False})
|
||||
input_transformer_manager = Instance('yap_ipython.yapi.YAPInputSplitter',
|
||||
(), {'line_input_checker': True})
|
||||
|
||||
logstart = Bool(False, help=
|
||||
"""
|
||||
@@ -476,8 +479,8 @@ class InteractiveShell(SingletonConfigurable):
|
||||
warn('As of yap_ipython 5.0 `PromptManager` config will have no effect'
|
||||
' and has been replaced by TerminalInteractiveShell.prompts_class')
|
||||
self.configurables = [self]
|
||||
self._yrun_cell = YAPRun._yrun_cell
|
||||
YAPRun.init(self)
|
||||
yrun = YAPRun( self)
|
||||
self._yrun_cell = yrun._yrun_cell
|
||||
|
||||
# These are relatively independent and stateless
|
||||
self.init_ipython_dir(ipython_dir)
|
||||
@@ -519,6 +522,8 @@ class InteractiveShell(SingletonConfigurable):
|
||||
# The following was in post_config_initialization
|
||||
self.init_inspector()
|
||||
self.raw_input_original = input
|
||||
self.input_splitter.engine(self.yapeng)
|
||||
self.input_transformer_manager.engine(self.yapeng)
|
||||
self.init_completer()
|
||||
# TODO: init_io() needs to happen before init_traceback handlers
|
||||
# because the traceback handlers hardcode the stdout/stderr streams.
|
||||
@@ -541,6 +546,8 @@ class InteractiveShell(SingletonConfigurable):
|
||||
self.events.trigger('shell_initialized', self)
|
||||
atexit.register(self.atexit_operations)
|
||||
|
||||
|
||||
|
||||
def get_ipython(self):
|
||||
"""Return the currently running yap_ipython instance."""
|
||||
return self
|
||||
@@ -1966,23 +1973,20 @@ class InteractiveShell(SingletonConfigurable):
|
||||
magic_run_completer, cd_completer, reset_completer)
|
||||
|
||||
self.Completer = YAPCompleter(shell=self,
|
||||
namespace=self.user_ns,
|
||||
global_namespace=self.user_global_ns,
|
||||
parent=self
|
||||
)
|
||||
self.configurables.append(self.Completer)
|
||||
|
||||
# Add custom completers to the basic ones built into IPCompleter
|
||||
sdisp = self.strdispatchers.get('complete_command', StrDispatch())
|
||||
self.strdispatchers['complete_command'] = sdisp
|
||||
self.Completer.custom_completers = sdisp
|
||||
|
||||
self.set_hook('complete_command', module_completer, str_key = 'import')
|
||||
self.set_hook('complete_command', module_completer, str_key = 'from')
|
||||
self.set_hook('complete_command', module_completer, str_key = '%aimport')
|
||||
self.set_hook('complete_command', magic_run_completer, str_key = '%run')
|
||||
self.set_hook('complete_command', cd_completer, str_key = '%cd')
|
||||
self.set_hook('complete_command', reset_completer, str_key = '%reset')
|
||||
# sdisp = self.strdispatchers.get('complete_command', StrDispatch())
|
||||
# self.strdispatchers['complete_command'] = sdisp
|
||||
# self.Completer.custom_completers = sdisp
|
||||
#
|
||||
# #self.set_hook('complete_command', module_completer, str_key = 'import')
|
||||
# #self.set_hook('complete_command', module_completer, str_key = 'from')
|
||||
# self.set_hook('complete_command', module_completer, str_key = '%aimport')
|
||||
# self.set_hook('complete_command', magic_run_completer, str_key = '%run')
|
||||
# self.set_hook('complete_command', cd_completer, str_key = '%cd')
|
||||
# self.set_hook('complete_command', reset_completer, str_key = '%reset')
|
||||
|
||||
|
||||
def complete(self, text, line=None, cursor_pos=None):
|
||||
@@ -2376,6 +2380,7 @@ class InteractiveShell(SingletonConfigurable):
|
||||
# code out there that may rely on this).
|
||||
self.prefilter = self.prefilter_manager.prefilter_lines
|
||||
|
||||
|
||||
def auto_rewrite_input(self, cmd):
|
||||
"""Print to the screen the rewritten form of the user's command.
|
||||
|
||||
@@ -2658,7 +2663,7 @@ class InteractiveShell(SingletonConfigurable):
|
||||
"""
|
||||
try:
|
||||
result = self._yrun_cell(
|
||||
self, raw_cell, store_history, silent, shell_futures)
|
||||
raw_cell, store_history, silent, shell_futures)
|
||||
finally:
|
||||
self.events.trigger('post_execute')
|
||||
if not silent:
|
||||
|
@@ -10,214 +10,37 @@
|
||||
* -
|
||||
*/
|
||||
|
||||
:- module(jupyter, [jupyter_query/3,
|
||||
ready/3,
|
||||
valid/3,
|
||||
errors/2]).
|
||||
:- module( jupyter,
|
||||
[jupyter_query/3,
|
||||
errors/2,
|
||||
ready/2,
|
||||
completion/2
|
||||
]
|
||||
).
|
||||
|
||||
:- use_module(library(yapi)).
|
||||
:- use_module(library(lists)).
|
||||
:- use_module(library(maplist)).
|
||||
:- use_module(library(python)).
|
||||
|
||||
:- python_import(sys).
|
||||
:- use_module(library(yapi)).
|
||||
:- use_module(library(lists)).
|
||||
:- use_module(library(maplist)).
|
||||
:- use_module(library(python)).
|
||||
|
||||
:- dynamic user:portray_message/2.
|
||||
:- multifile user:portray_message/2.
|
||||
:- python_import(sys).
|
||||
|
||||
jupyter_query(Self, Cell, Line ) :-
|
||||
setup_call_cleanup(
|
||||
user:jupyter_query(Self, Cell, Line ) :-
|
||||
setup_call_cleanup(
|
||||
enter_cell(Self),
|
||||
jupyter_cell(Self, Cell, Line),
|
||||
exit_cell(Self)
|
||||
).
|
||||
|
||||
ready(_Self, Line ) :-
|
||||
blank( Line ),
|
||||
!.
|
||||
ready(Self, Line ) :-
|
||||
errors( Self, Line ),
|
||||
\+ syntax_error(_,_).
|
||||
|
||||
errors( Self, Text ) :-
|
||||
setup_call_cleanup(
|
||||
open_events( Self, Text, Stream),
|
||||
clauses(Self, Stream),
|
||||
close_events( Self )
|
||||
).
|
||||
|
||||
clauses(Self, Stream) :-
|
||||
repeat,
|
||||
read_clause(Stream, Cl, [term_position(_Pos), syntax_errors(fail)] ),
|
||||
command( Self, Cl ),
|
||||
Cl == end_of_file,
|
||||
!.
|
||||
|
||||
command( _Self, ( :- op(Prio,Assoc,Name) ) ) :-
|
||||
addop(Prio,Assoc,Name).
|
||||
|
||||
command( _Self, ( :- module(Name, Exports) )) :-
|
||||
retract( active_module( M0 ) ),
|
||||
atom_concat( '__m0_', Name, M ),
|
||||
assert( active_module(M) ),
|
||||
assert( undo( active_module(M0) ) ),
|
||||
maplist( addop2(M), Exports).
|
||||
|
||||
|
||||
addop(Prio,Assoc,Name) :-
|
||||
(
|
||||
current_op(OPrio, SimilarAssoc, Name),
|
||||
op(Prio, Assoc, Name),
|
||||
matched_op(Assoc, SimilarAssoc)
|
||||
->
|
||||
assertz( undo(op( OPrio, Assoc, Name ) ) )
|
||||
;
|
||||
assertz( undo(op( 0, Assoc, Name ) ) )
|
||||
).
|
||||
|
||||
addop2(M, op(Prio, Assoc, Name)) :-
|
||||
addop( Prio, Assoc, M:Name ).
|
||||
|
||||
matched_op(A, B) :-
|
||||
optype( A, T),
|
||||
optype( B, T).
|
||||
|
||||
optype(fx,pre).
|
||||
optype(fy,pre).
|
||||
optype(xfx,in).
|
||||
optype(xfy,in).
|
||||
optype(yfx,in).
|
||||
optype(yfy,in).
|
||||
optype(xf,pos).
|
||||
optype(yf,pos).
|
||||
|
||||
:- dynamic user:portray_message/2.
|
||||
:- multifile user:portray_message/2.
|
||||
|
||||
:- dynamic syntax_error/2, undo/1.
|
||||
|
||||
open_events(Self, Text, Stream) :-
|
||||
Self.errors := [],
|
||||
open_mem_read_stream( Text, Stream ),
|
||||
assert((user:portray_message(_Severity, error(error(syntax_error(_),info(between(_,LN,_), _FileName, CharPos, _Details)))) :-
|
||||
assert( syntax_error(LN,CharPos) )
|
||||
)).
|
||||
|
||||
close_events( Self ) :-
|
||||
retract( undo(G) ),
|
||||
call(G),
|
||||
fail.
|
||||
close_events( Self ) :-
|
||||
retract( syntax_error( L, N )),
|
||||
Self.errors := [t(L,N)] + Self.errors,
|
||||
fail.
|
||||
close_events( _ ).
|
||||
|
||||
cell2pq( Cell, ``, ``) :-
|
||||
sub_string(Cell, 0, 2, _, `%%`),
|
||||
string_code(3, Cell, Code),
|
||||
code_type(Code, alpha),
|
||||
!.
|
||||
cell2pq( Cell, P, Q, N) :-
|
||||
sub_string(Cell, 0, 1, _, `%`),
|
||||
string_codes(Cell, [Code|Codes]),
|
||||
code_type(Code, alpha),
|
||||
skip(10, Codes, Rest, LineF,Line1),
|
||||
skip_blanks(Rest, Body, Line1,Line0),
|
||||
reverse(Body, RBody),
|
||||
cell2pq2(RBody, Ps, Qs, N),
|
||||
extend(Ps, Qs, LineF, Line0, NPs, NQs),
|
||||
string_codes(P, NPs),
|
||||
string_codes(Q, NQs).
|
||||
cell2pq( Cell, P, Q, N) :-
|
||||
string_codes(Cell, Codes),
|
||||
reverse(Codes, RCodes),
|
||||
cell2pq2(RCodes, NPs, NQs, N),
|
||||
string_codes(P, NPs),
|
||||
string_codes(Q, NQs).
|
||||
|
||||
%
|
||||
% terminates with dot
|
||||
%
|
||||
cell2pq2(RCodes, NP, NQ, N) :-
|
||||
skip_allblanks( RCodes, [C|Rest], L1, L0),
|
||||
( C =:= "."
|
||||
->
|
||||
N = 1,
|
||||
RP = RCodes,
|
||||
RQ = ""
|
||||
;
|
||||
skip_to_blank_line( [C|Rest], RP, L0, []),
|
||||
RQ = L1,
|
||||
(
|
||||
C =:= "*"
|
||||
->
|
||||
N = -1
|
||||
;
|
||||
N=1
|
||||
)
|
||||
),
|
||||
reverse(RP,NP),
|
||||
reverse(RQ,NQ).
|
||||
|
||||
/**
|
||||
* @pred skip( Char, Input, Remainder, Begin, End)
|
||||
*
|
||||
* split the list according to character _Char_:
|
||||
*
|
||||
* - _Remainder_ is what is after chars
|
||||
* - _Begin_-_End_ represents what is before char.
|
||||
*
|
||||
*/
|
||||
skip(_, "", "") -->
|
||||
!,
|
||||
[].
|
||||
skip(C, [C|Cs], Cs) -->
|
||||
!,
|
||||
[C].
|
||||
skip(C, [OC|Cs], Line) -->
|
||||
[OC],
|
||||
skip(C,Cs, Line).
|
||||
|
||||
skip_to_blank_line("", "") -->
|
||||
!.
|
||||
skip_to_blank_line(Cs, Left) -->
|
||||
blank_line(Cs, Left),
|
||||
!,
|
||||
[].
|
||||
skip_to_blank_line(Cs, Line) -->
|
||||
line(Cs, Line),
|
||||
!.
|
||||
|
||||
blank_line("", []) --> [].
|
||||
blank_line([10|Cs], Cs) -->
|
||||
[10],
|
||||
!.
|
||||
blank_line([C|Cs], Rest) -->
|
||||
{ code_type(C, white)},
|
||||
!,
|
||||
[C],
|
||||
blank_line(Cs, Rest).
|
||||
|
||||
line("", []) -->
|
||||
[].
|
||||
line([10|Cs], Cs) -->
|
||||
[10],
|
||||
!.
|
||||
line([C|Cs], Rest) -->
|
||||
[C],
|
||||
line(Cs,Rest).
|
||||
|
||||
|
||||
jupyter_cell(_Self, Cell, _) :-
|
||||
% stop_low_level_trace,
|
||||
jupyter_consult(Cell),
|
||||
fail.
|
||||
jupyter_cell( _Self, _, Line ) :-
|
||||
blank( Line ),
|
||||
!.
|
||||
jupyter_cell( Self, _, [] ) :- !.
|
||||
jupyter_cell( Self, _, Line ) :-
|
||||
% start_low_level_trace,
|
||||
python_query( Self, Line ).
|
||||
|
||||
jupyter_consult(Text) :-
|
||||
@@ -250,14 +73,14 @@ exit_cell(_Self) :-
|
||||
close( user_error).
|
||||
|
||||
|
||||
completions(S, Self) :-
|
||||
user:completions(S, Self) :-
|
||||
open_mem_read_stream(S, St),
|
||||
scan_to_list(St, Tokens),
|
||||
close(St),
|
||||
reverse(Tokens, RTokens),
|
||||
strip_final_tokens(RTokens, MyTokens),
|
||||
setof( Completion, complete(MyTokens, Completion), Cs),
|
||||
Self.completions := Cs.
|
||||
Self.matches := Cs.
|
||||
|
||||
|
||||
strip_final_tokens(['EOT'|Ts], Ts) :- !.
|
||||
@@ -347,3 +170,88 @@ cont(0, F, P, P0) :-
|
||||
atom_concat( F, P, P0 ).
|
||||
cont( _, F, P, PB ):-
|
||||
atom_concat( [F, P, '('], PB ).
|
||||
|
||||
|
||||
ready(_Self, Line ) :-
|
||||
blank( Line ),
|
||||
!.
|
||||
ready(Self, Line ) :-
|
||||
errors( Self, Line ),
|
||||
\+ syntax_error(_,_).
|
||||
|
||||
user:errors( Self, Text ) :-
|
||||
setup_call_cleanup(
|
||||
open_events( Self, Text, Stream),
|
||||
clauses(Self, Stream),
|
||||
close_events( Self )
|
||||
).
|
||||
|
||||
clauses(Self, Stream) :-
|
||||
repeat,
|
||||
read_clause(Stream, Cl, [term_position(_Pos), syntax_errors(fail)] ),
|
||||
command( Self, Cl ),
|
||||
Cl == end_of_file,
|
||||
!.
|
||||
|
||||
command(_, end_of_file) :- !.
|
||||
|
||||
command( _Self, ( :- op(Prio,Assoc,Name) ) ) :-
|
||||
addop(Prio,Assoc,Name).
|
||||
|
||||
command( _Self, ( :- module(Name, Exports) )) :-
|
||||
retract( active_module( M0 ) ),
|
||||
atom_concat( '__m0_', Name, M ),
|
||||
assert( active_module(M) ),
|
||||
assert( undo( active_module(M0) ) ),
|
||||
maplist( addop2(M), Exports).
|
||||
|
||||
|
||||
addop(Prio,Assoc,Name) :-
|
||||
(
|
||||
current_op(OPrio, SimilarAssoc, Name),
|
||||
op(Prio, Assoc, Name),
|
||||
matched_op(Assoc, SimilarAssoc)
|
||||
->
|
||||
assertz( undo(op( OPrio, Assoc, Name ) ) )
|
||||
;
|
||||
assertz( undo(op( 0, Assoc, Name ) ) )
|
||||
).
|
||||
|
||||
addop2(M, op(Prio, Assoc, Name)) :-
|
||||
addop( Prio, Assoc, M:Name ).
|
||||
|
||||
matched_op(A, B) :-
|
||||
optype( A, T),
|
||||
optype( B, T).
|
||||
|
||||
optype(fx,pre).
|
||||
optype(fy,pre).
|
||||
optype(xfx,in).
|
||||
optype(xfy,in).
|
||||
optype(yfx,in).
|
||||
optype(yfy,in).
|
||||
optype(xf,pos).
|
||||
optype(yf,pos).
|
||||
|
||||
:- dynamic user:portray_message/2.
|
||||
:- multifile user:portray_message/2.
|
||||
|
||||
:- dynamic syntax_error/4, undo/1.
|
||||
|
||||
open_events(Self, Text, Stream) :-
|
||||
Self.errors := [],
|
||||
open_mem_read_stream( Text, Stream ),
|
||||
assert((user:portray_message(_Severity, error(syntax_error(Cause),info(between(_,LN,_), _FileName, CharPos, Details))) :-
|
||||
assert( syntax_error(Cause,LN,CharPos,Details) )
|
||||
)).
|
||||
|
||||
close_events( Self ) :-
|
||||
retract( undo(G) ),
|
||||
call(G),
|
||||
fail.
|
||||
close_events( Self ) :-
|
||||
retract( syntax_error( C, L, N, A )),
|
||||
Self.errors := [t(C,L,N,A)] + Self.errors,
|
||||
fail.
|
||||
close_events( _ ).
|
||||
|
||||
|
@@ -3,8 +3,8 @@ import sys
|
||||
|
||||
from yap_ipython.core.debugger import Pdb
|
||||
|
||||
from yap_ipython.core.completer import IPCompleter
|
||||
from .ptutils import IPythonPTCompleter
|
||||
from yap_ipython.yapi import YAPCompleter
|
||||
#from .ptutils import IPythonPTCompleter
|
||||
from .shortcuts import suspend_to_bg, cursor_in_leading_ws
|
||||
|
||||
from prompt_toolkit.enums import DEFAULT_BUFFER
|
||||
|
@@ -33,7 +33,7 @@ from .debugger import TerminalPdb, Pdb
|
||||
from .magics import TerminalMagics
|
||||
from .pt_inputhooks import get_inputhook_name_and_func
|
||||
from .prompts import Prompts, ClassicPrompts, RichPromptDisplayHook
|
||||
from .ptutils import IPythonPTCompleter, IPythonPTLexer
|
||||
#from .ptutils import IPythonPTCompleter, IPythonPTLexer
|
||||
from .shortcuts import register_ipython_shortcuts
|
||||
|
||||
DISPLAY_BANNER_DEPRECATED = object()
|
||||
@@ -269,8 +269,8 @@ class TerminalInteractiveShell(InteractiveShell):
|
||||
editing_mode=editing_mode,
|
||||
key_bindings_registry=kbmanager.registry,
|
||||
history=history,
|
||||
completer=IPythonPTCompleter(shell=self,
|
||||
patch_stdout=patch_stdout),
|
||||
# completer=IPythonPTCompleter(shell=self,
|
||||
# patch_stdout=patch_stdout),
|
||||
enable_history_search=True,
|
||||
style=self.style,
|
||||
mouse_support=self.mouse_support,
|
||||
|
@@ -18,7 +18,7 @@ from traitlets.config.loader import Config
|
||||
from traitlets.config.application import boolean_flag, catch_config_error
|
||||
from yap_ipython.core import release
|
||||
from yap_ipython.core import usage
|
||||
from yap_ipython.core.completer import IPCompleter
|
||||
from yap_ipython.yapi import YAPCompleter
|
||||
from yap_ipython.core.crashhandler import CrashHandler
|
||||
from yap_ipython.core.formatters import PlainTextFormatter
|
||||
from yap_ipython.core.history import HistoryManager
|
||||
@@ -177,7 +177,7 @@ class LocateIPythonApp(BaseYAPApplication):
|
||||
|
||||
|
||||
class TerminalIPythonApp(BaseYAPApplication, InteractiveShellApp):
|
||||
name = u'ipython'
|
||||
name = u'yap'
|
||||
description = usage.cl_usage
|
||||
crash_handler_class = IPAppCrashHandler
|
||||
examples = _examples
|
||||
@@ -202,7 +202,7 @@ class TerminalIPythonApp(BaseYAPApplication, InteractiveShellApp):
|
||||
HistoryManager,
|
||||
ProfileDir,
|
||||
PlainTextFormatter,
|
||||
IPCompleter,
|
||||
YAPCompleter,
|
||||
ScriptMagics,
|
||||
LoggingMagics,
|
||||
StoreMagics,
|
||||
@@ -301,7 +301,7 @@ class TerminalIPythonApp(BaseYAPApplication, InteractiveShellApp):
|
||||
argv[idx] = '--pylab'
|
||||
|
||||
return super(TerminalIPythonApp, self).parse_command_line(argv)
|
||||
|
||||
|
||||
@catch_config_error
|
||||
def initialize(self, argv=None):
|
||||
"""Do actions after construct, but before starting the app."""
|
||||
|
@@ -2,17 +2,23 @@ import os
|
||||
import sys
|
||||
import abc
|
||||
import math
|
||||
import itertools
|
||||
|
||||
|
||||
from typing import Iterator, List, Tuple, Iterable, Union
|
||||
from traitlets import Bool, Enum, observe, Int
|
||||
|
||||
try:
|
||||
import yap4py.yapi
|
||||
from yap4py.yapi import Engine
|
||||
except:
|
||||
print("Could not load _yap dll.")
|
||||
from yap_ipython.core import interactiveshell
|
||||
from yap_ipython.core.completer import IPCompleter
|
||||
from yap_ipython.core.completer import Completer, Completion
|
||||
from yap_ipython.utils.strdispatch import StrDispatch
|
||||
# import yap_ipython.core
|
||||
from traitlets import Instance
|
||||
|
||||
from yap_ipython.core.inputsplitter import *
|
||||
from yap_ipython.core.inputtransformer import *
|
||||
from pygments import highlight
|
||||
from pygments.lexers.prolog import PrologLexer
|
||||
from pygments.formatters import HtmlFormatter
|
||||
@@ -26,18 +32,278 @@ library = namedtuple('library', 'list')
|
||||
v = namedtuple('_', 'slot')
|
||||
load_files = namedtuple('load_files', 'file ofile args')
|
||||
python_query= namedtuple('python_query', 'query_mgr string')
|
||||
JupyterQuery = namedtuple('jupyter_query', 'self text query')
|
||||
jupyter_query = namedtuple('jupyter_query', 'self text query')
|
||||
enter_cell = namedtuple('enter_cell', 'self' )
|
||||
exit_cell = namedtuple('exit_cell', 'self' )
|
||||
completions = namedtuple('completions', 'txt self' )
|
||||
errors = namedtuple('errors', 'self text' )
|
||||
|
||||
class YAPCompleter:
|
||||
|
||||
def __init__(self,
|
||||
shell=None, namespace=None, global_namespace=None,
|
||||
parent=None,
|
||||
):
|
||||
self.completions = None
|
||||
class YAPInputSplitter(InputSplitter):
|
||||
"""An input splitter that recognizes all of iyap's special syntax."""
|
||||
|
||||
# String with raw, untransformed input.
|
||||
source_raw = ''
|
||||
|
||||
# Flag to track when a transformer has stored input that it hasn't given
|
||||
# back yet.
|
||||
transformer_accumulating = False
|
||||
|
||||
# Flag to track when assemble_yap_lines has stored input that it hasn't
|
||||
# given back yet.
|
||||
within_yap_line = False
|
||||
|
||||
# Private attributes
|
||||
|
||||
# List with lines of raw input accumulated so far.
|
||||
_buffer_raw = None
|
||||
|
||||
def __init__(self, line_input_checker=True, physical_line_transforms=None,
|
||||
logical_line_transforms=None):
|
||||
self._buffer_raw = []
|
||||
self._validate = True
|
||||
self.yapeng = None
|
||||
|
||||
if physical_line_transforms is not None:
|
||||
self.physical_line_transforms = physical_line_transforms
|
||||
else:
|
||||
self.physical_line_transforms = [
|
||||
leading_indent(),
|
||||
classic_prompt(),
|
||||
ipy_prompt(),
|
||||
cellmagic(end_on_blank_line=line_input_checker),
|
||||
]
|
||||
|
||||
self.assemble_logical_lines = assemble_logical_lines()
|
||||
if logical_line_transforms is not None:
|
||||
self.logical_line_transforms = logical_line_transforms
|
||||
else:
|
||||
self.logical_line_transforms = [
|
||||
help_end(),
|
||||
escaped_commands(),
|
||||
assign_from_magic(),
|
||||
assign_from_system(),
|
||||
]
|
||||
|
||||
|
||||
@property
|
||||
def transforms(self):
|
||||
"Quick access to all transformers."
|
||||
return self.physical_line_transforms + \
|
||||
[self.assemble_logical_lines] + self.logical_line_transforms
|
||||
|
||||
|
||||
@property
|
||||
def transforms_in_use(self):
|
||||
"""Transformers, excluding logical line transformers if we're in a
|
||||
Python line."""
|
||||
t = self.physical_line_transforms + \
|
||||
[self.assemble_logical_lines] + self.logical_line_transforms
|
||||
|
||||
def engine(self, engine):
|
||||
self.yapeng = engine
|
||||
|
||||
def validQuery(self, text, line=None):
|
||||
"""Return whether a legal query
|
||||
"""
|
||||
if not line:
|
||||
(_,line,_) = self.shell.prolog_cell(text)
|
||||
line = line.strip().rstrip()
|
||||
if not line:
|
||||
return False
|
||||
self.errors = []
|
||||
self.yapeng.mgoal(errors(self, line),"user")
|
||||
return self.errors != []
|
||||
|
||||
|
||||
def reset(self):
|
||||
"""Reset the input buffer and associated state."""
|
||||
#super(YAPInputSplitter, self).reset()
|
||||
self._buffer_raw[:] = []
|
||||
self.source_raw = ''
|
||||
self.transformer_accumulating = False
|
||||
|
||||
for t in self.transforms:
|
||||
try:
|
||||
t.reset()
|
||||
except SyntaxError:
|
||||
# Nothing that calls reset() expects to handle transformer
|
||||
# errors
|
||||
pass
|
||||
|
||||
def flush_transformers(self):
|
||||
def _flush(transform, outs):
|
||||
"""yield transformed lines
|
||||
|
||||
always strings, never None
|
||||
|
||||
transform: the current transform
|
||||
outs: an iterable of previously transformed inputs.
|
||||
Each may be multiline, which will be passed
|
||||
one line at a time to transform.
|
||||
"""
|
||||
for out in outs:
|
||||
for line in out.splitlines():
|
||||
# push one line at a time
|
||||
tmp = transform.push(line)
|
||||
if tmp is not None:
|
||||
yield tmp
|
||||
|
||||
# reset the transform
|
||||
tmp = transform.reset()
|
||||
if tmp is not None:
|
||||
yield tmp
|
||||
|
||||
out = []
|
||||
|
||||
for t in self.transforms:
|
||||
out = _flush(t, out)
|
||||
|
||||
out = list(out)
|
||||
if out:
|
||||
self._store('\n'.join(out))
|
||||
|
||||
def raw_reset(self):
|
||||
"""Return raw input only and perform a full reset.
|
||||
"""
|
||||
out = self.source_raw
|
||||
self.reset()
|
||||
return out
|
||||
|
||||
def source_reset(self):
|
||||
try:
|
||||
self.flush_transformers()
|
||||
return self.source
|
||||
finally:
|
||||
self.reset()
|
||||
|
||||
def push_accepts_more(self):
|
||||
if self.transformer_accumulating:
|
||||
return True
|
||||
else:
|
||||
return self,validQuery(self.source)
|
||||
|
||||
def transform_cell(self, cell):
|
||||
"""Process and translate a cell of input.
|
||||
"""
|
||||
self.reset()
|
||||
try:
|
||||
self.push(cell)
|
||||
self.flush_transformers()
|
||||
return self.source
|
||||
finally:
|
||||
self.reset()
|
||||
|
||||
def push(self, lines):
|
||||
"""Push one or more lines of yap_ipython input.
|
||||
|
||||
This stores the given lines and returns a status code indicating
|
||||
whether the code forms a complete Python block or not, after processing
|
||||
all input lines for special yap_ipython syntax.
|
||||
|
||||
Any exceptions generated in compilation are swallowed, but if an
|
||||
exception was produced, the method returns True.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
lines : string
|
||||
One or more lines of Python input.
|
||||
|
||||
Returns
|
||||
-------
|
||||
is_complete : boolean
|
||||
True if the current input source (the result of the current input
|
||||
plus prior inputs) forms a complete Python execution block. Note that
|
||||
this value is also stored as a private attribute (_is_complete), so it
|
||||
can be queried at any time.
|
||||
"""
|
||||
|
||||
# We must ensure all input is pure unicode
|
||||
lines = cast_unicode(lines, self.encoding)
|
||||
# ''.splitlines() --> [], but we need to push the empty line to transformers
|
||||
lines_list = lines.splitlines()
|
||||
if not lines_list:
|
||||
lines_list = ['']
|
||||
|
||||
# Store raw source before applying any transformations to it. Note
|
||||
# that this must be done *after* the reset() call that would otherwise
|
||||
# flush the buffer.
|
||||
self._store(lines, self._buffer_raw, 'source_raw')
|
||||
|
||||
transformed_lines_list = []
|
||||
for line in lines_list:
|
||||
transformed = self._transform_line(line)
|
||||
if transformed is not None:
|
||||
transformed_lines_list.append(transformed)
|
||||
if transformed_lines_list:
|
||||
transformed_lines = '\n'.join(transformed_lines_list)
|
||||
else:
|
||||
# Got nothing back from transformers - they must be waiting for
|
||||
# more input.
|
||||
return False
|
||||
|
||||
def _transform_line(self, line):
|
||||
"""Push a line of input code through the various transformers.
|
||||
|
||||
Returns any output from the transformers, or None if a transformer
|
||||
is accumulating lines.
|
||||
|
||||
Sets self.transformer_accumulating as a side effect.
|
||||
"""
|
||||
def _accumulating(dbg):
|
||||
#print(dbg)
|
||||
self.transformer_accumulating = True
|
||||
return None
|
||||
|
||||
for transformer in self.physical_line_transforms:
|
||||
line = transformer.push(line)
|
||||
if line is None:
|
||||
return _accumulating(transformer)
|
||||
|
||||
for transformer in self.logical_line_transforms:
|
||||
line = transformer.push(line)
|
||||
if line is None:
|
||||
return _accumulating(transformer)
|
||||
|
||||
|
||||
#print("transformers clear") #debug
|
||||
self.transformer_accumulating = False
|
||||
return line
|
||||
|
||||
|
||||
class YAPCompleter(Completer):
|
||||
|
||||
greedy = Bool(False,
|
||||
help="""Activate greedy completion
|
||||
PENDING DEPRECTION. this is now mostly taken care of with Jedi.
|
||||
|
||||
This will enable completion on elements of lists, results of function calls, etc.,
|
||||
but can be unsafe because the code is actually evaluated on TAB.
|
||||
"""
|
||||
).tag(config=True)
|
||||
|
||||
debug = Bool(default_value=False,
|
||||
help='Enable debug for the Completer. Mostly print extra '
|
||||
'information for experimental jedi integration.') \
|
||||
.tag(config=True)
|
||||
|
||||
backslash_combining_completions = Bool(True,
|
||||
help="Enable unicode completions, e.g. \\alpha<tab> . "
|
||||
"Includes completion of latex commands, unicode names, and expanding "
|
||||
"unicode characters back to latex commands.").tag(config=True)
|
||||
|
||||
|
||||
|
||||
def __init__(self, namespace=None, global_namespace=None, shell=None, **kwargs):
|
||||
"""Create a new completer for the command line.
|
||||
|
||||
Completer(namespace=ns, global_namespace=ns2) -> completer instance.
|
||||
|
||||
"""
|
||||
|
||||
self.shell = shell
|
||||
self.magic_escape = ESC_MAGIC
|
||||
super(Completer, self).__init__(**kwargs)
|
||||
|
||||
def complete(self, text, line=None, cursor_pos=None):
|
||||
"""Return the completed text and a list of completions.
|
||||
@@ -50,6 +316,9 @@ class YAPCompleter:
|
||||
instead a line/position pair are given. In this case, the
|
||||
completer itself will split the line like readline does.
|
||||
|
||||
This is called successively with state == 0, 1, 2, ... until it
|
||||
returns None. The completion should begin with 'text'.
|
||||
|
||||
line : string, optional
|
||||
The complete line that text is part of.
|
||||
|
||||
@@ -79,65 +348,197 @@ class YAPCompleter:
|
||||
In [2]: _ip.complete('x.l')
|
||||
Out[2]: ('x.l', ['x.ljust', 'x.lower', 'x.lstrip'])
|
||||
"""
|
||||
|
||||
if not text:
|
||||
text = line[:cursor_pos]
|
||||
self.yapeng.goal(completions(text, self))
|
||||
return text, self.completions
|
||||
return self.completions(text, cursor_pos)
|
||||
|
||||
# def _init__(self, **kwargs) -> None:
|
||||
# PyCompleter.__init__(**kwargs__)
|
||||
|
||||
def magic_matches(self, text):
|
||||
"""Match magics"""
|
||||
# Get all shell magics now rather than statically, so magics loaded at
|
||||
# runtime show up too.
|
||||
lsm = self.shell.magics_manager.lsmagic()
|
||||
line_magics = lsm['line']
|
||||
cell_magics = lsm['cell']
|
||||
pre = self.magic_escape
|
||||
pre2 = pre+pre
|
||||
|
||||
explicit_magic = text.startswith(pre)
|
||||
|
||||
# Completion logic:
|
||||
# - user gives %%: only do cell magics
|
||||
# - user gives %: do both line and cell magics
|
||||
# - no prefix: do both
|
||||
# In other words, line magics are skipped if the user gives %% explicitly
|
||||
#
|
||||
# We also exclude magics that match any currently visible names:
|
||||
# https://github.com/ipython/ipython/issues/4877, unless the user has
|
||||
# typed a %:
|
||||
# https://github.com/ipython/ipython/issues/10754
|
||||
bare_text = text.lstrip(pre)
|
||||
global_matches = []
|
||||
if not explicit_magic:
|
||||
def matches(magic):
|
||||
"""
|
||||
Filter magics, in particular remove magics that match
|
||||
a name present in global namespace.
|
||||
"""
|
||||
return ( magic.startswith(bare_text) and
|
||||
magic not in global_matches )
|
||||
else:
|
||||
def matches(magic):
|
||||
return magic.startswith(bare_text)
|
||||
|
||||
comp = [ pre2+m for m in cell_magics if matches(m)]
|
||||
if not text.startswith(pre2):
|
||||
comp += [ pre+m for m in line_magics if matches(m)]
|
||||
|
||||
return comp
|
||||
|
||||
def magic_config_matches(self, text:str) -> List[str]:
|
||||
""" Match class names and attributes for %config magic """
|
||||
texts = text.strip().split()
|
||||
|
||||
if len(texts) > 0 and (texts[0] == 'config' or texts[0] == '%config'):
|
||||
# get all configuration classes
|
||||
classes = sorted(set([ c for c in self.shell.configurables
|
||||
if c.__class__.class_traits(config=True)
|
||||
]), key=lambda x: x.__class__.__name__)
|
||||
classnames = [ c.__class__.__name__ for c in classes ]
|
||||
|
||||
# return all classnames if config or %config is given
|
||||
if len(texts) == 1:
|
||||
return classnames
|
||||
|
||||
# match classname
|
||||
classname_texts = texts[1].split('.')
|
||||
classname = classname_texts[0]
|
||||
classname_matches = [ c for c in classnames
|
||||
if c.startswith(classname) ]
|
||||
|
||||
# return matched classes or the matched class with attributes
|
||||
if texts[1].find('.') < 0:
|
||||
return classname_matches
|
||||
elif len(classname_matches) == 1 and \
|
||||
classname_matches[0] == classname:
|
||||
cls = classes[classnames.index(classname)].__class__
|
||||
help = cls.class_get_help()
|
||||
# strip leading '--' from cl-args:
|
||||
help = re.sub(re.compile(r'^--', re.MULTILINE), '', help)
|
||||
return [ attr.split('=')[0]
|
||||
for attr in help.strip().splitlines()
|
||||
if attr.startswith(texts[1]) ]
|
||||
return []
|
||||
|
||||
|
||||
def magic_color_matches(self, text:str) -> List[str] :
|
||||
""" Match color schemes for %colors magic"""
|
||||
texts = text.split()
|
||||
if text.endswith(' '):
|
||||
# .split() strips off the trailing whitespace. Add '' back
|
||||
# so that: '%colors ' -> ['%colors', '']
|
||||
texts.append('')
|
||||
|
||||
if len(texts) == 2 and (texts[0] == 'colors' or texts[0] == '%colors'):
|
||||
prefix = texts[1]
|
||||
return [ color for color in InspectColors.keys()
|
||||
if color.startswith(prefix) ]
|
||||
return []
|
||||
|
||||
|
||||
|
||||
class YAPLineProcessor:
|
||||
|
||||
def __init__(self,
|
||||
shell
|
||||
):
|
||||
self.engine = shell.engine
|
||||
|
||||
def validQuery(self, text, line=None, cursor_pos=None):
|
||||
"""Return whether a legal query
|
||||
def completions(self, text, offset):
|
||||
"""
|
||||
if not line:
|
||||
(_,line,_) = self.prolog_cell(text)
|
||||
line = line.strip().rstrip()
|
||||
if not line:
|
||||
return False
|
||||
self.yapeng.goal(errors(text, line))
|
||||
return not self.errors
|
||||
Returns an iterator over the possible completions
|
||||
|
||||
# def _init__(self, **kwargs) -> None:
|
||||
# PyCompleter.__init__(**kwargs__)
|
||||
.. warning:: Unstable
|
||||
|
||||
This function is unstable, API may change without warning.
|
||||
It will also raise unless use in proper context manager.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
|
||||
text:str
|
||||
Full text of the current input, multi line string.
|
||||
offset:int
|
||||
Integer representing the position of the cursor in ``text``. Offset
|
||||
is 0-based indexed.
|
||||
|
||||
Yields
|
||||
------
|
||||
:any:`Completion` object
|
||||
|
||||
|
||||
The cursor on a text can either be seen as being "in between"
|
||||
characters or "On" a character depending on the interface visible to
|
||||
the user. For consistency the cursor being on "in between" characters X
|
||||
and Y is equivalent to the cursor being "on" character Y, that is to say
|
||||
the character the cursor is on is considered as being after the cursor.
|
||||
|
||||
Combining characters may span more that one position in the
|
||||
text.
|
||||
|
||||
|
||||
.. note::
|
||||
|
||||
If ``IPCompleter.debug`` is :any:`True` will yield a ``--jedi/ipython--``
|
||||
fake Completion token to distinguish completion returned by Jedi
|
||||
and usual yap_ipython completion.
|
||||
|
||||
.. note::
|
||||
|
||||
Completions are not completely deduplicated yet. If identical
|
||||
completions are coming from different sources this function does not
|
||||
ensure that each completion object will only be present once.
|
||||
"""
|
||||
self.matches = []
|
||||
prolog_res = self.shell.yapeng.mgoal(completions(text, self), "user")
|
||||
magic_res = self.magic_matches(text)
|
||||
|
||||
return text, self.matches+magic_res
|
||||
|
||||
|
||||
|
||||
class YAPRun():
|
||||
class YAPRun:
|
||||
"""An enhanced, interactive shell for YAP."""
|
||||
|
||||
def init(self):
|
||||
self.yapeng = yap4py.yapi.Engine()
|
||||
def __init__(self, shell):
|
||||
self.shell = shell
|
||||
self.yapeng = Engine()
|
||||
self.yapeng.goal(use_module(library("jupyter")))
|
||||
self.q = None
|
||||
self.run = False
|
||||
self.port = None
|
||||
self.shell.port = None
|
||||
self.shell.yapeng = self.yapeng
|
||||
self._get_exc_info = shell._get_exc_info
|
||||
|
||||
def syntaxErrors(self, text):
|
||||
"""Return whether a legal query
|
||||
"""
|
||||
if not text:
|
||||
return []
|
||||
self.errors=[]
|
||||
self.yapeng.mgoal(errors(self,text),"user")
|
||||
return self.errors
|
||||
|
||||
def jupyter_query(self, s):
|
||||
# import pdb; pdb.set_trace()
|
||||
#
|
||||
# construct a self.query from a one-line string
|
||||
# self.q is opaque to Python
|
||||
self.bindings = {}
|
||||
iterations = 0
|
||||
self.shell.bindings = {}
|
||||
if self.q and s != self.os:
|
||||
self.q.close()
|
||||
self.q = None
|
||||
if not self.q:
|
||||
#import pdb; pdb.set_trace()
|
||||
self.port = "call"
|
||||
program,query,iterations = YAPRun.prolog_cell(self,s)
|
||||
self.q = self.yapeng.query(JupyterQuery(self, program, query))
|
||||
self.Solutions = []
|
||||
self.shell.port = "call"
|
||||
program,query,_ = self.prolog_cell(s)
|
||||
self.q = self.yapeng.query(jupyter_query(self, program, query))
|
||||
self.shell.Solutions = []
|
||||
if not self.q:
|
||||
return True, []
|
||||
self.os = s
|
||||
@@ -162,27 +563,26 @@ class YAPRun():
|
||||
# deterministic = one solution
|
||||
#Dict = {}
|
||||
#engine.goal(show_answer( q.namedVars(), Dict))
|
||||
self.Solutions += [self.bindings]
|
||||
if self.port == "exit":
|
||||
self.shell.Solutions += [self.shell.bindings]
|
||||
if self.shell.port == "exit":
|
||||
# done
|
||||
self.q.close()
|
||||
self.q = None
|
||||
self.os = ""
|
||||
return True, self.Solutions
|
||||
return True, self.shell.Solutions
|
||||
if iterations == 0:
|
||||
return True, self.Solutions
|
||||
return True, self.shell.Solutions
|
||||
else:
|
||||
print("No (more) answers")
|
||||
self.q.close()
|
||||
self.q = None
|
||||
self.os = ''
|
||||
return True, self.Solutions
|
||||
return True, self.shell.Solutions
|
||||
|
||||
def answer(self, q):
|
||||
try:
|
||||
return q.next()
|
||||
except Exception as e:
|
||||
print(e.args[1])
|
||||
self.yapeng.goal(exit_cell(self))
|
||||
return False, None
|
||||
|
||||
@@ -236,69 +636,75 @@ class YAPRun():
|
||||
result = interactiveshell.ExecutionResult(info)
|
||||
|
||||
if (raw_cell == "") or raw_cell.isspace():
|
||||
self.last_execution_succeeded = True
|
||||
self.shell.last_execution_succeeded = True
|
||||
return result
|
||||
|
||||
if silent:
|
||||
store_history = False
|
||||
|
||||
if store_history:
|
||||
result.execution_count = self.execution_count+1
|
||||
result.execution_count = self.shell.execution_count+1
|
||||
|
||||
def error_before_exec(value):
|
||||
result.error_before_exec = value
|
||||
self.last_execution_succeeded = False
|
||||
self.shell.last_execution_succeeded = False
|
||||
return result
|
||||
|
||||
self.events.trigger('pre_execute')
|
||||
self.shell.events.trigger('pre_execute')
|
||||
if not silent:
|
||||
self.events.trigger('pre_run_cell')
|
||||
|
||||
self.shell.events.trigger('pre_run_cell')
|
||||
# If any of our input transformation (input_transformer_manager or
|
||||
# prefilter_manager) raises an exception, we store it in this variable
|
||||
# so that we can display the error after logging the input and storing
|
||||
# it in the history.
|
||||
preprocessing_exc_tuple = None
|
||||
try:
|
||||
# Static input transformations
|
||||
cell = self.input_transformer_manager.transform_cell(raw_cell)
|
||||
except SyntaxError:
|
||||
preprocessing_exc_tuple = self.syntax_error() # sys.exc_info()
|
||||
# try:
|
||||
# # Static input transformations
|
||||
# cell = self.shell.input_transformer_manager.transform_cell(raw_cell)
|
||||
# except SyntaxError:
|
||||
# preprocessing_exc_tuple = self.shell.syntax_error() # sys.exc_info()
|
||||
cell = raw_cell # cell has to exist so it can be stored/logged
|
||||
# else:
|
||||
# # import pdb; pdb.set_trace()
|
||||
# if False and len(cell.splitlines()) == 1:
|
||||
# # Dynamic transformations - only applied for single line commands
|
||||
# with self.builtin_trap:
|
||||
# with self.shell.builtin_trap:
|
||||
# try:
|
||||
# # use prefilter_lines to handle trailing newlines
|
||||
# # restore trailing newline for ast.parse
|
||||
# cell = self.prefilter_manager.prefilter_lines(cell) + '\n'
|
||||
# cell = self.shell.prefilter_manager.prefilter_lines(cell) + '\n'
|
||||
# except Exception:
|
||||
# # don't allow prefilter errors to crash IPython
|
||||
# preprocessing_exc_tuple = sys.exc_info()
|
||||
|
||||
|
||||
e for i in self.syntaxErrors(raw_cell):
|
||||
try:
|
||||
(what,lin,_,text) = i
|
||||
e = SyntaxError(what, ("<string>", lin, 1, text))
|
||||
raise e
|
||||
except SyntaxError:
|
||||
self.shell.showsyntaxerror( )
|
||||
preprocessing_exc_tuple = sys.exc_info()
|
||||
|
||||
# Store raw and processed history
|
||||
if store_history:
|
||||
self.history_manager.store_inputs(self.execution_count,
|
||||
self.shell.history_manager.store_inputs(self.shell.execution_count,
|
||||
cell, raw_cell)
|
||||
if not silent:
|
||||
self.logger.log(cell, raw_cell)
|
||||
self.shell.logger.log(cell, raw_cell)
|
||||
|
||||
# # Display the exception if input processing failed.
|
||||
# if preprocessing_exc_tuple is not None:
|
||||
# self.showtraceback(preprocessing_exc_tuple)
|
||||
# if store_history:
|
||||
# self.execution_count += 1
|
||||
# self.shell.execution_count += 1
|
||||
# return error_before_exec(preprocessing_exc_tuple[2])
|
||||
|
||||
# Our own compiler remembers the __future__ environment. If we want to
|
||||
# run code with a separate __future__ environment, use the default
|
||||
# compiler
|
||||
# compiler = self.compile if shell_futures else CachingCompiler()
|
||||
|
||||
cell_name = str( self.execution_count)
|
||||
# compiler = self.shell.compile if shell_futures else CachingCompiler()
|
||||
cell_name = str( self.shell.execution_count)
|
||||
|
||||
if cell[0] == '%':
|
||||
if cell[1] == '%':
|
||||
@@ -309,53 +715,53 @@ class YAPRun():
|
||||
mcell = cell.lstrip('%')
|
||||
txt0 = mcell.split(maxsplit = 2, sep = '\n')
|
||||
txt = txt0[0].split(maxsplit = 2)
|
||||
magic = txt[0]
|
||||
magic = txt[0]
|
||||
if len(txt) == 2:
|
||||
line = txt[1]
|
||||
else:
|
||||
line = ""
|
||||
if linec:
|
||||
self.run_line_magic(magic, line)
|
||||
self.shell.run_line_magic(magic, line)
|
||||
if len(txt0) == 2:
|
||||
cell = txt0[1]
|
||||
else:
|
||||
cellArea = ""
|
||||
else:
|
||||
self.run_cell_magic(magic, line, cell)
|
||||
self.shell.run_cell_magic(magic, line, cell)
|
||||
return
|
||||
# Give the displayhook a reference to our ExecutionResult so it
|
||||
# can fill in the output value.
|
||||
self.displayhook.exec_result = result
|
||||
self.shell.displayhook.exec_result = result
|
||||
has_raised = False
|
||||
try:
|
||||
self.bindings = dict = {}
|
||||
state = YAPRun.jupyter_query(self, cell)
|
||||
self.shell.bindings = dict = {}
|
||||
state = self.jupyter_query( cell)
|
||||
if state:
|
||||
self.last_execution_succeeded = True
|
||||
self.shell.last_execution_succeeded = True
|
||||
result.result = (True, dict)
|
||||
else:
|
||||
self.last_execution_succeeded = True
|
||||
self.shell.last_execution_succeeded = True
|
||||
result.result = (True, {})
|
||||
except Exception as e:
|
||||
print(e)
|
||||
has_raised = True
|
||||
result.result = False
|
||||
|
||||
self.last_execution_succeeded = not has_raised
|
||||
self.shell.last_execution_succeeded = not has_raised
|
||||
|
||||
# Reset this so later displayed values do not modify the
|
||||
# ExecutionResult
|
||||
self.displayhook.exec_result = None
|
||||
self.events.trigger('post_execute')
|
||||
self.shell.displayhook.exec_result = None
|
||||
self.shell.events.trigger('post_execute')
|
||||
if not silent:
|
||||
self.events.trigger('post_run_cell')
|
||||
self.shell.events.trigger('post_run_cell')
|
||||
|
||||
if store_history:
|
||||
# Write output to the database. Does nothing unless
|
||||
# history output logging is enabled.
|
||||
self.history_manager.store_output(self.execution_count)
|
||||
self.shell.history_manager.store_output(self.shell.execution_count)
|
||||
# Each cell is a *single* input, regardless of how many lines it has
|
||||
self.execution_count += 1
|
||||
self.shell.execution_count += 1
|
||||
|
||||
return result
|
||||
|
||||
@@ -377,12 +783,14 @@ class YAPRun():
|
||||
its = 0
|
||||
s0 = ''
|
||||
for c in s:
|
||||
if c == '\n' or c.isblank():
|
||||
s0 += [c]
|
||||
if c == '\n' or c.isspace():
|
||||
s0 += c
|
||||
break
|
||||
sf = ''
|
||||
for c in reversed(s):
|
||||
if c == '\n' or c.isblank():
|
||||
sf += [c]+sf
|
||||
if c == '\n' or c.isspace():
|
||||
sf += c
|
||||
break
|
||||
[program,x,query] = s.rpartition('\n')
|
||||
if query == '':
|
||||
query = program
|
||||
|
@@ -15,7 +15,7 @@ from .zmqshell import ZMQInteractiveShell
|
||||
|
||||
try:
|
||||
from yap_ipython.core.completer import rectify_completions as _rectify_completions, provisionalcompleter as _provisionalcompleter
|
||||
_use_experimental_60_completion = True
|
||||
_use_experimental_60_completion = False
|
||||
except ImportError:
|
||||
_use_experimental_60_completion = False
|
||||
|
||||
@@ -203,6 +203,7 @@ class YAPKernel(KernelBase):
|
||||
self._forward_input(allow_stdin)
|
||||
|
||||
reply_content = {}
|
||||
import trace;
|
||||
try:
|
||||
res = shell.run_cell(code, store_history=store_history, silent=silent)
|
||||
finally:
|
||||
|
@@ -35,14 +35,14 @@ from jupyter_client import write_connection_file
|
||||
from jupyter_client.connect import ConnectionFileMixin
|
||||
|
||||
# local imports
|
||||
from .iostream import IOPubThread
|
||||
from .heartbeat import Heartbeat
|
||||
from .ipkernel import YAPKernel
|
||||
from .parentpoller import ParentPollerUnix, ParentPollerWindows
|
||||
from yap_kernel.iostream import IOPubThread
|
||||
from yap_kernel.heartbeat import Heartbeat
|
||||
from yap_kernel.ipkernel import YAPKernel
|
||||
from yap_kernel.parentpoller import ParentPollerUnix, ParentPollerWindows
|
||||
from jupyter_client.session import (
|
||||
Session, session_flags, session_aliases,
|
||||
)
|
||||
from .zmqshell import ZMQInteractiveShell
|
||||
from yap_kernel.zmqshell import ZMQInteractiveShell
|
||||
|
||||
#-----------------------------------------------------------------------------
|
||||
# Flags and Aliases
|
||||
|
Binary file not shown.
Before Width: | Height: | Size: 1.1 KiB |
Binary file not shown.
Before Width: | Height: | Size: 2.1 KiB |
@@ -235,7 +235,7 @@ class KernelMagics(Magics):
|
||||
|
||||
-n <number>
|
||||
Open the editor at a specified line number. By default, the yap_ipython
|
||||
editor hook uses the unix syntax 'editor +N filename', but you can
|
||||
editor hook uses the unix syntax//i 'editor +N filename', but you can
|
||||
configure this by providing your own modified hook if your favorite
|
||||
editor supports line-number specifications with a different syntax.
|
||||
|
||||
|
Reference in New Issue
Block a user