Add files using upload-large-folder tool
Browse files- venv/Lib/site-packages/decorator.py +459 -0
- venv/Lib/site-packages/ipykernel_launcher.py +18 -0
- venv/Lib/site-packages/ipython_pygments_lexers.py +582 -0
- venv/Lib/site-packages/isympy.py +342 -0
- venv/Lib/site-packages/jsonpointer.py +348 -0
- venv/Lib/site-packages/jupyter.py +7 -0
- venv/Lib/site-packages/nest_asyncio.py +219 -0
- venv/Lib/site-packages/numpy-2.2.5-cp312-cp312-win_amd64.whl +0 -0
- venv/Lib/site-packages/pandocfilters.py +304 -0
- venv/Lib/site-packages/pylab.py +3 -0
- venv/Lib/site-packages/pythoncom.py +4 -0
- venv/Lib/site-packages/pywin32.version.txt +1 -0
- venv/Lib/site-packages/rfc3339_validator.py +51 -0
- venv/Lib/site-packages/rfc3986_validator.py +106 -0
- venv/etc/jupyter/jupyter_server_config.d/jupyter_server_terminals.json +7 -0
- venv/etc/jupyter/jupyter_server_config.d/jupyterlab.json +7 -0
- venv/etc/jupyter/jupyter_server_config.d/notebook.json +7 -0
- venv/etc/jupyter/jupyter_server_config.d/notebook_shim.json +7 -0
- venv/etc/jupyter/labconfig/page_config.json +3 -0
- venv/etc/jupyter/nbconfig/notebook.d/widgetsnbextension.json +5 -0
venv/Lib/site-packages/decorator.py
ADDED
@@ -0,0 +1,459 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
# ######################### LICENSE ############################ #
|
2 |
+
|
3 |
+
# Copyright (c) 2005-2025, Michele Simionato
|
4 |
+
# All rights reserved.
|
5 |
+
|
6 |
+
# Redistribution and use in source and binary forms, with or without
|
7 |
+
# modification, are permitted provided that the following conditions are
|
8 |
+
# met:
|
9 |
+
|
10 |
+
# Redistributions of source code must retain the above copyright
|
11 |
+
# notice, this list of conditions and the following disclaimer.
|
12 |
+
# Redistributions in bytecode form must reproduce the above copyright
|
13 |
+
# notice, this list of conditions and the following disclaimer in
|
14 |
+
# the documentation and/or other materials provided with the
|
15 |
+
# distribution.
|
16 |
+
|
17 |
+
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
18 |
+
# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
19 |
+
# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
20 |
+
# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
21 |
+
# HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
|
22 |
+
# INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
23 |
+
# BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
|
24 |
+
# OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
|
25 |
+
# ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
|
26 |
+
# TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
|
27 |
+
# USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
|
28 |
+
# DAMAGE.
|
29 |
+
|
30 |
+
"""
|
31 |
+
Decorator module, see
|
32 |
+
https://github.com/micheles/decorator/blob/master/docs/documentation.md
|
33 |
+
for the documentation.
|
34 |
+
"""
|
35 |
+
import re
|
36 |
+
import sys
|
37 |
+
import inspect
|
38 |
+
import operator
|
39 |
+
import itertools
|
40 |
+
import functools
|
41 |
+
from contextlib import _GeneratorContextManager
|
42 |
+
from inspect import getfullargspec, iscoroutinefunction, isgeneratorfunction
|
43 |
+
|
44 |
+
__version__ = '5.2.1'
|
45 |
+
|
46 |
+
DEF = re.compile(r'\s*def\s*([_\w][_\w\d]*)\s*\(')
|
47 |
+
POS = inspect.Parameter.POSITIONAL_OR_KEYWORD
|
48 |
+
EMPTY = inspect.Parameter.empty
|
49 |
+
|
50 |
+
|
51 |
+
# this is not used anymore in the core, but kept for backward compatibility
|
52 |
+
class FunctionMaker(object):
|
53 |
+
"""
|
54 |
+
An object with the ability to create functions with a given signature.
|
55 |
+
It has attributes name, doc, module, signature, defaults, dict and
|
56 |
+
methods update and make.
|
57 |
+
"""
|
58 |
+
|
59 |
+
# Atomic get-and-increment provided by the GIL
|
60 |
+
_compile_count = itertools.count()
|
61 |
+
|
62 |
+
# make pylint happy
|
63 |
+
args = varargs = varkw = defaults = kwonlyargs = kwonlydefaults = ()
|
64 |
+
|
65 |
+
def __init__(self, func=None, name=None, signature=None,
|
66 |
+
defaults=None, doc=None, module=None, funcdict=None):
|
67 |
+
self.shortsignature = signature
|
68 |
+
if func:
|
69 |
+
# func can be a class or a callable, but not an instance method
|
70 |
+
self.name = func.__name__
|
71 |
+
if self.name == '<lambda>': # small hack for lambda functions
|
72 |
+
self.name = '_lambda_'
|
73 |
+
self.doc = func.__doc__
|
74 |
+
self.module = func.__module__
|
75 |
+
if inspect.isroutine(func) or isinstance(func, functools.partial):
|
76 |
+
argspec = getfullargspec(func)
|
77 |
+
self.annotations = getattr(func, '__annotations__', {})
|
78 |
+
for a in ('args', 'varargs', 'varkw', 'defaults', 'kwonlyargs',
|
79 |
+
'kwonlydefaults'):
|
80 |
+
setattr(self, a, getattr(argspec, a))
|
81 |
+
for i, arg in enumerate(self.args):
|
82 |
+
setattr(self, 'arg%d' % i, arg)
|
83 |
+
allargs = list(self.args)
|
84 |
+
allshortargs = list(self.args)
|
85 |
+
if self.varargs:
|
86 |
+
allargs.append('*' + self.varargs)
|
87 |
+
allshortargs.append('*' + self.varargs)
|
88 |
+
elif self.kwonlyargs:
|
89 |
+
allargs.append('*') # single star syntax
|
90 |
+
for a in self.kwonlyargs:
|
91 |
+
allargs.append('%s=None' % a)
|
92 |
+
allshortargs.append('%s=%s' % (a, a))
|
93 |
+
if self.varkw:
|
94 |
+
allargs.append('**' + self.varkw)
|
95 |
+
allshortargs.append('**' + self.varkw)
|
96 |
+
self.signature = ', '.join(allargs)
|
97 |
+
self.shortsignature = ', '.join(allshortargs)
|
98 |
+
self.dict = func.__dict__.copy()
|
99 |
+
# func=None happens when decorating a caller
|
100 |
+
if name:
|
101 |
+
self.name = name
|
102 |
+
if signature is not None:
|
103 |
+
self.signature = signature
|
104 |
+
if defaults:
|
105 |
+
self.defaults = defaults
|
106 |
+
if doc:
|
107 |
+
self.doc = doc
|
108 |
+
if module:
|
109 |
+
self.module = module
|
110 |
+
if funcdict:
|
111 |
+
self.dict = funcdict
|
112 |
+
# check existence required attributes
|
113 |
+
assert hasattr(self, 'name')
|
114 |
+
if not hasattr(self, 'signature'):
|
115 |
+
raise TypeError('You are decorating a non function: %s' % func)
|
116 |
+
|
117 |
+
def update(self, func, **kw):
|
118 |
+
"""
|
119 |
+
Update the signature of func with the data in self
|
120 |
+
"""
|
121 |
+
func.__name__ = self.name
|
122 |
+
func.__doc__ = getattr(self, 'doc', None)
|
123 |
+
func.__dict__ = getattr(self, 'dict', {})
|
124 |
+
func.__defaults__ = self.defaults
|
125 |
+
func.__kwdefaults__ = self.kwonlydefaults or None
|
126 |
+
func.__annotations__ = getattr(self, 'annotations', None)
|
127 |
+
try:
|
128 |
+
frame = sys._getframe(3)
|
129 |
+
except AttributeError: # for IronPython and similar implementations
|
130 |
+
callermodule = '?'
|
131 |
+
else:
|
132 |
+
callermodule = frame.f_globals.get('__name__', '?')
|
133 |
+
func.__module__ = getattr(self, 'module', callermodule)
|
134 |
+
func.__dict__.update(kw)
|
135 |
+
|
136 |
+
def make(self, src_templ, evaldict=None, addsource=False, **attrs):
|
137 |
+
"""
|
138 |
+
Make a new function from a given template and update the signature
|
139 |
+
"""
|
140 |
+
src = src_templ % vars(self) # expand name and signature
|
141 |
+
evaldict = evaldict or {}
|
142 |
+
mo = DEF.search(src)
|
143 |
+
if mo is None:
|
144 |
+
raise SyntaxError('not a valid function template\n%s' % src)
|
145 |
+
name = mo.group(1) # extract the function name
|
146 |
+
names = set([name] + [arg.strip(' *') for arg in
|
147 |
+
self.shortsignature.split(',')])
|
148 |
+
for n in names:
|
149 |
+
if n in ('_func_', '_call_'):
|
150 |
+
raise NameError('%s is overridden in\n%s' % (n, src))
|
151 |
+
|
152 |
+
if not src.endswith('\n'): # add a newline for old Pythons
|
153 |
+
src += '\n'
|
154 |
+
|
155 |
+
# Ensure each generated function has a unique filename for profilers
|
156 |
+
# (such as cProfile) that depend on the tuple of (<filename>,
|
157 |
+
# <definition line>, <function name>) being unique.
|
158 |
+
filename = '<decorator-gen-%d>' % next(self._compile_count)
|
159 |
+
try:
|
160 |
+
code = compile(src, filename, 'single')
|
161 |
+
exec(code, evaldict)
|
162 |
+
except Exception:
|
163 |
+
print('Error in generated code:', file=sys.stderr)
|
164 |
+
print(src, file=sys.stderr)
|
165 |
+
raise
|
166 |
+
func = evaldict[name]
|
167 |
+
if addsource:
|
168 |
+
attrs['__source__'] = src
|
169 |
+
self.update(func, **attrs)
|
170 |
+
return func
|
171 |
+
|
172 |
+
@classmethod
|
173 |
+
def create(cls, obj, body, evaldict, defaults=None,
|
174 |
+
doc=None, module=None, addsource=True, **attrs):
|
175 |
+
"""
|
176 |
+
Create a function from the strings name, signature and body.
|
177 |
+
evaldict is the evaluation dictionary. If addsource is true an
|
178 |
+
attribute __source__ is added to the result. The attributes attrs
|
179 |
+
are added, if any.
|
180 |
+
"""
|
181 |
+
if isinstance(obj, str): # "name(signature)"
|
182 |
+
name, rest = obj.strip().split('(', 1)
|
183 |
+
signature = rest[:-1] # strip a right parens
|
184 |
+
func = None
|
185 |
+
else: # a function
|
186 |
+
name = None
|
187 |
+
signature = None
|
188 |
+
func = obj
|
189 |
+
self = cls(func, name, signature, defaults, doc, module)
|
190 |
+
ibody = '\n'.join(' ' + line for line in body.splitlines())
|
191 |
+
caller = evaldict.get('_call_') # when called from `decorate`
|
192 |
+
if caller and iscoroutinefunction(caller):
|
193 |
+
body = ('async def %(name)s(%(signature)s):\n' + ibody).replace(
|
194 |
+
'return', 'return await')
|
195 |
+
else:
|
196 |
+
body = 'def %(name)s(%(signature)s):\n' + ibody
|
197 |
+
return self.make(body, evaldict, addsource, **attrs)
|
198 |
+
|
199 |
+
|
200 |
+
def fix(args, kwargs, sig):
|
201 |
+
"""
|
202 |
+
Fix args and kwargs to be consistent with the signature
|
203 |
+
"""
|
204 |
+
ba = sig.bind(*args, **kwargs)
|
205 |
+
ba.apply_defaults() # needed for test_dan_schult
|
206 |
+
return ba.args, ba.kwargs
|
207 |
+
|
208 |
+
|
209 |
+
def decorate(func, caller, extras=(), kwsyntax=False):
|
210 |
+
"""
|
211 |
+
Decorates a function/generator/coroutine using a caller.
|
212 |
+
If kwsyntax is True calling the decorated functions with keyword
|
213 |
+
syntax will pass the named arguments inside the ``kw`` dictionary,
|
214 |
+
even if such argument are positional, similarly to what functools.wraps
|
215 |
+
does. By default kwsyntax is False and the the arguments are untouched.
|
216 |
+
"""
|
217 |
+
sig = inspect.signature(func)
|
218 |
+
if isinstance(func, functools.partial):
|
219 |
+
func = functools.update_wrapper(func, func.func)
|
220 |
+
if iscoroutinefunction(caller):
|
221 |
+
async def fun(*args, **kw):
|
222 |
+
if not kwsyntax:
|
223 |
+
args, kw = fix(args, kw, sig)
|
224 |
+
return await caller(func, *(extras + args), **kw)
|
225 |
+
elif isgeneratorfunction(caller):
|
226 |
+
def fun(*args, **kw):
|
227 |
+
if not kwsyntax:
|
228 |
+
args, kw = fix(args, kw, sig)
|
229 |
+
for res in caller(func, *(extras + args), **kw):
|
230 |
+
yield res
|
231 |
+
else:
|
232 |
+
def fun(*args, **kw):
|
233 |
+
if not kwsyntax:
|
234 |
+
args, kw = fix(args, kw, sig)
|
235 |
+
return caller(func, *(extras + args), **kw)
|
236 |
+
|
237 |
+
fun.__name__ = func.__name__
|
238 |
+
fun.__doc__ = func.__doc__
|
239 |
+
fun.__wrapped__ = func
|
240 |
+
fun.__signature__ = sig
|
241 |
+
fun.__qualname__ = func.__qualname__
|
242 |
+
# builtin functions like defaultdict.__setitem__ lack many attributes
|
243 |
+
try:
|
244 |
+
fun.__defaults__ = func.__defaults__
|
245 |
+
except AttributeError:
|
246 |
+
pass
|
247 |
+
try:
|
248 |
+
fun.__kwdefaults__ = func.__kwdefaults__
|
249 |
+
except AttributeError:
|
250 |
+
pass
|
251 |
+
try:
|
252 |
+
fun.__annotations__ = func.__annotations__
|
253 |
+
except AttributeError:
|
254 |
+
pass
|
255 |
+
try:
|
256 |
+
fun.__module__ = func.__module__
|
257 |
+
except AttributeError:
|
258 |
+
pass
|
259 |
+
try:
|
260 |
+
fun.__name__ = func.__name__
|
261 |
+
except AttributeError: # happens with old versions of numpy.vectorize
|
262 |
+
func.__name__ == 'noname'
|
263 |
+
try:
|
264 |
+
fun.__dict__.update(func.__dict__)
|
265 |
+
except AttributeError:
|
266 |
+
pass
|
267 |
+
return fun
|
268 |
+
|
269 |
+
|
270 |
+
def decoratorx(caller):
|
271 |
+
"""
|
272 |
+
A version of "decorator" implemented via "exec" and not via the
|
273 |
+
Signature object. Use this if you are want to preserve the `.__code__`
|
274 |
+
object properties (https://github.com/micheles/decorator/issues/129).
|
275 |
+
"""
|
276 |
+
def dec(func):
|
277 |
+
return FunctionMaker.create(
|
278 |
+
func,
|
279 |
+
"return _call_(_func_, %(shortsignature)s)",
|
280 |
+
dict(_call_=caller, _func_=func),
|
281 |
+
__wrapped__=func, __qualname__=func.__qualname__)
|
282 |
+
return dec
|
283 |
+
|
284 |
+
|
285 |
+
def decorator(caller, _func=None, kwsyntax=False):
|
286 |
+
"""
|
287 |
+
decorator(caller) converts a caller function into a decorator
|
288 |
+
"""
|
289 |
+
if _func is not None: # return a decorated function
|
290 |
+
# this is obsolete behavior; you should use decorate instead
|
291 |
+
return decorate(_func, caller, (), kwsyntax)
|
292 |
+
# else return a decorator function
|
293 |
+
sig = inspect.signature(caller)
|
294 |
+
dec_params = [p for p in sig.parameters.values() if p.kind is POS]
|
295 |
+
|
296 |
+
def dec(func=None, *args, **kw):
|
297 |
+
na = len(args) + 1
|
298 |
+
extras = args + tuple(kw.get(p.name, p.default)
|
299 |
+
for p in dec_params[na:]
|
300 |
+
if p.default is not EMPTY)
|
301 |
+
if func is None:
|
302 |
+
return lambda func: decorate(func, caller, extras, kwsyntax)
|
303 |
+
else:
|
304 |
+
return decorate(func, caller, extras, kwsyntax)
|
305 |
+
dec.__signature__ = sig.replace(parameters=dec_params)
|
306 |
+
dec.__name__ = caller.__name__
|
307 |
+
dec.__doc__ = caller.__doc__
|
308 |
+
dec.__wrapped__ = caller
|
309 |
+
dec.__qualname__ = caller.__qualname__
|
310 |
+
dec.__kwdefaults__ = getattr(caller, '__kwdefaults__', None)
|
311 |
+
dec.__dict__.update(caller.__dict__)
|
312 |
+
return dec
|
313 |
+
|
314 |
+
|
315 |
+
# ####################### contextmanager ####################### #
|
316 |
+
|
317 |
+
|
318 |
+
class ContextManager(_GeneratorContextManager):
|
319 |
+
def __init__(self, g, *a, **k):
|
320 |
+
_GeneratorContextManager.__init__(self, g, a, k)
|
321 |
+
|
322 |
+
def __call__(self, func):
|
323 |
+
def caller(f, *a, **k):
|
324 |
+
with self.__class__(self.func, *self.args, **self.kwds):
|
325 |
+
return f(*a, **k)
|
326 |
+
return decorate(func, caller)
|
327 |
+
|
328 |
+
|
329 |
+
_contextmanager = decorator(ContextManager)
|
330 |
+
|
331 |
+
|
332 |
+
def contextmanager(func):
|
333 |
+
# Enable Pylint config: contextmanager-decorators=decorator.contextmanager
|
334 |
+
return _contextmanager(func)
|
335 |
+
|
336 |
+
|
337 |
+
# ############################ dispatch_on ############################ #
|
338 |
+
|
339 |
+
def append(a, vancestors):
|
340 |
+
"""
|
341 |
+
Append ``a`` to the list of the virtual ancestors, unless it is already
|
342 |
+
included.
|
343 |
+
"""
|
344 |
+
add = True
|
345 |
+
for j, va in enumerate(vancestors):
|
346 |
+
if issubclass(va, a):
|
347 |
+
add = False
|
348 |
+
break
|
349 |
+
if issubclass(a, va):
|
350 |
+
vancestors[j] = a
|
351 |
+
add = False
|
352 |
+
if add:
|
353 |
+
vancestors.append(a)
|
354 |
+
|
355 |
+
|
356 |
+
# inspired from simplegeneric by P.J. Eby and functools.singledispatch
|
357 |
+
def dispatch_on(*dispatch_args):
|
358 |
+
"""
|
359 |
+
Factory of decorators turning a function into a generic function
|
360 |
+
dispatching on the given arguments.
|
361 |
+
"""
|
362 |
+
assert dispatch_args, 'No dispatch args passed'
|
363 |
+
dispatch_str = '(%s,)' % ', '.join(dispatch_args)
|
364 |
+
|
365 |
+
def check(arguments, wrong=operator.ne, msg=''):
|
366 |
+
"""Make sure one passes the expected number of arguments"""
|
367 |
+
if wrong(len(arguments), len(dispatch_args)):
|
368 |
+
raise TypeError('Expected %d arguments, got %d%s' %
|
369 |
+
(len(dispatch_args), len(arguments), msg))
|
370 |
+
|
371 |
+
def gen_func_dec(func):
|
372 |
+
"""Decorator turning a function into a generic function"""
|
373 |
+
|
374 |
+
# first check the dispatch arguments
|
375 |
+
argset = set(getfullargspec(func).args)
|
376 |
+
if not set(dispatch_args) <= argset:
|
377 |
+
raise NameError('Unknown dispatch arguments %s' % dispatch_str)
|
378 |
+
|
379 |
+
typemap = {}
|
380 |
+
|
381 |
+
def vancestors(*types):
|
382 |
+
"""
|
383 |
+
Get a list of sets of virtual ancestors for the given types
|
384 |
+
"""
|
385 |
+
check(types)
|
386 |
+
ras = [[] for _ in range(len(dispatch_args))]
|
387 |
+
for types_ in typemap:
|
388 |
+
for t, type_, ra in zip(types, types_, ras):
|
389 |
+
if issubclass(t, type_) and type_ not in t.mro():
|
390 |
+
append(type_, ra)
|
391 |
+
return [set(ra) for ra in ras]
|
392 |
+
|
393 |
+
def ancestors(*types):
|
394 |
+
"""
|
395 |
+
Get a list of virtual MROs, one for each type
|
396 |
+
"""
|
397 |
+
check(types)
|
398 |
+
lists = []
|
399 |
+
for t, vas in zip(types, vancestors(*types)):
|
400 |
+
n_vas = len(vas)
|
401 |
+
if n_vas > 1:
|
402 |
+
raise RuntimeError(
|
403 |
+
'Ambiguous dispatch for %s: %s' % (t, vas))
|
404 |
+
elif n_vas == 1:
|
405 |
+
va, = vas
|
406 |
+
mro = type('t', (t, va), {}).mro()[1:]
|
407 |
+
else:
|
408 |
+
mro = t.mro()
|
409 |
+
lists.append(mro[:-1]) # discard t and object
|
410 |
+
return lists
|
411 |
+
|
412 |
+
def register(*types):
|
413 |
+
"""
|
414 |
+
Decorator to register an implementation for the given types
|
415 |
+
"""
|
416 |
+
check(types)
|
417 |
+
|
418 |
+
def dec(f):
|
419 |
+
check(getfullargspec(f).args, operator.lt, ' in ' + f.__name__)
|
420 |
+
typemap[types] = f
|
421 |
+
return f
|
422 |
+
return dec
|
423 |
+
|
424 |
+
def dispatch_info(*types):
|
425 |
+
"""
|
426 |
+
An utility to introspect the dispatch algorithm
|
427 |
+
"""
|
428 |
+
check(types)
|
429 |
+
lst = []
|
430 |
+
for ancs in itertools.product(*ancestors(*types)):
|
431 |
+
lst.append(tuple(a.__name__ for a in ancs))
|
432 |
+
return lst
|
433 |
+
|
434 |
+
def _dispatch(dispatch_args, *args, **kw):
|
435 |
+
types = tuple(type(arg) for arg in dispatch_args)
|
436 |
+
try: # fast path
|
437 |
+
f = typemap[types]
|
438 |
+
except KeyError:
|
439 |
+
pass
|
440 |
+
else:
|
441 |
+
return f(*args, **kw)
|
442 |
+
combinations = itertools.product(*ancestors(*types))
|
443 |
+
next(combinations) # the first one has been already tried
|
444 |
+
for types_ in combinations:
|
445 |
+
f = typemap.get(types_)
|
446 |
+
if f is not None:
|
447 |
+
return f(*args, **kw)
|
448 |
+
|
449 |
+
# else call the default implementation
|
450 |
+
return func(*args, **kw)
|
451 |
+
|
452 |
+
return FunctionMaker.create(
|
453 |
+
func, 'return _f_(%s, %%(shortsignature)s)' % dispatch_str,
|
454 |
+
dict(_f_=_dispatch), register=register, default=func,
|
455 |
+
typemap=typemap, vancestors=vancestors, ancestors=ancestors,
|
456 |
+
dispatch_info=dispatch_info, __wrapped__=func)
|
457 |
+
|
458 |
+
gen_func_dec.__name__ = 'dispatch_on' + dispatch_str
|
459 |
+
return gen_func_dec
|
venv/Lib/site-packages/ipykernel_launcher.py
ADDED
@@ -0,0 +1,18 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
"""Entry point for launching an IPython kernel.
|
2 |
+
|
3 |
+
This is separate from the ipykernel package so we can avoid doing imports until
|
4 |
+
after removing the cwd from sys.path.
|
5 |
+
"""
|
6 |
+
|
7 |
+
import sys
|
8 |
+
from pathlib import Path
|
9 |
+
|
10 |
+
if __name__ == "__main__":
|
11 |
+
# Remove the CWD from sys.path while we load stuff.
|
12 |
+
# This is added back by InteractiveShellApp.init_path()
|
13 |
+
if sys.path[0] == "" or Path(sys.path[0]) == Path.cwd():
|
14 |
+
del sys.path[0]
|
15 |
+
|
16 |
+
from ipykernel import kernelapp as app
|
17 |
+
|
18 |
+
app.launch_new_instance()
|
venv/Lib/site-packages/ipython_pygments_lexers.py
ADDED
@@ -0,0 +1,582 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
# -*- coding: utf-8 -*-
|
2 |
+
"""
|
3 |
+
Defines a variety of Pygments lexers for highlighting IPython code.
|
4 |
+
|
5 |
+
This includes:
|
6 |
+
|
7 |
+
IPythonLexer, IPython3Lexer
|
8 |
+
Lexers for pure IPython (python + magic/shell commands)
|
9 |
+
|
10 |
+
IPythonPartialTracebackLexer, IPythonTracebackLexer
|
11 |
+
Supports 2.x and 3.x via keyword `python3`. The partial traceback
|
12 |
+
lexer reads everything but the Python code appearing in a traceback.
|
13 |
+
The full lexer combines the partial lexer with an IPython lexer.
|
14 |
+
|
15 |
+
IPythonConsoleLexer
|
16 |
+
A lexer for IPython console sessions, with support for tracebacks.
|
17 |
+
|
18 |
+
IPyLexer
|
19 |
+
A friendly lexer which examines the first line of text and from it,
|
20 |
+
decides whether to use an IPython lexer or an IPython console lexer.
|
21 |
+
This is probably the only lexer that needs to be explicitly added
|
22 |
+
to Pygments.
|
23 |
+
|
24 |
+
"""
|
25 |
+
# -----------------------------------------------------------------------------
|
26 |
+
# Copyright (c) 2013, the IPython Development Team.
|
27 |
+
#
|
28 |
+
# Distributed under the terms of the Modified BSD License.
|
29 |
+
#
|
30 |
+
# The full license is in the file COPYING.txt, distributed with this software.
|
31 |
+
# -----------------------------------------------------------------------------
|
32 |
+
|
33 |
+
__version__ = "1.1.1"
|
34 |
+
|
35 |
+
# Standard library
|
36 |
+
import re
|
37 |
+
|
38 |
+
# Third party
|
39 |
+
from pygments.lexers import (
|
40 |
+
BashLexer,
|
41 |
+
HtmlLexer,
|
42 |
+
JavascriptLexer,
|
43 |
+
RubyLexer,
|
44 |
+
PerlLexer,
|
45 |
+
Python2Lexer,
|
46 |
+
Python3Lexer,
|
47 |
+
TexLexer,
|
48 |
+
)
|
49 |
+
from pygments.lexer import (
|
50 |
+
Lexer,
|
51 |
+
DelegatingLexer,
|
52 |
+
RegexLexer,
|
53 |
+
do_insertions,
|
54 |
+
bygroups,
|
55 |
+
using,
|
56 |
+
)
|
57 |
+
from pygments.token import (
|
58 |
+
Generic,
|
59 |
+
Keyword,
|
60 |
+
Literal,
|
61 |
+
Name,
|
62 |
+
Operator,
|
63 |
+
Other,
|
64 |
+
Text,
|
65 |
+
Error,
|
66 |
+
)
|
67 |
+
|
68 |
+
|
69 |
+
line_re = re.compile(".*?\n")
|
70 |
+
|
71 |
+
__all__ = [
|
72 |
+
"IPython3Lexer",
|
73 |
+
"IPythonLexer",
|
74 |
+
"IPythonPartialTracebackLexer",
|
75 |
+
"IPythonTracebackLexer",
|
76 |
+
"IPythonConsoleLexer",
|
77 |
+
"IPyLexer",
|
78 |
+
]
|
79 |
+
|
80 |
+
|
81 |
+
ipython_tokens = [
|
82 |
+
(
|
83 |
+
r"(?s)(\s*)(%%capture)([^\n]*\n)(.*)",
|
84 |
+
bygroups(Text, Operator, Text, using(Python3Lexer)),
|
85 |
+
),
|
86 |
+
(
|
87 |
+
r"(?s)(\s*)(%%debug)([^\n]*\n)(.*)",
|
88 |
+
bygroups(Text, Operator, Text, using(Python3Lexer)),
|
89 |
+
),
|
90 |
+
(
|
91 |
+
r"(?is)(\s*)(%%html)([^\n]*\n)(.*)",
|
92 |
+
bygroups(Text, Operator, Text, using(HtmlLexer)),
|
93 |
+
),
|
94 |
+
(
|
95 |
+
r"(?s)(\s*)(%%javascript)([^\n]*\n)(.*)",
|
96 |
+
bygroups(Text, Operator, Text, using(JavascriptLexer)),
|
97 |
+
),
|
98 |
+
(
|
99 |
+
r"(?s)(\s*)(%%js)([^\n]*\n)(.*)",
|
100 |
+
bygroups(Text, Operator, Text, using(JavascriptLexer)),
|
101 |
+
),
|
102 |
+
(
|
103 |
+
r"(?s)(\s*)(%%latex)([^\n]*\n)(.*)",
|
104 |
+
bygroups(Text, Operator, Text, using(TexLexer)),
|
105 |
+
),
|
106 |
+
(
|
107 |
+
r"(?s)(\s*)(%%perl)([^\n]*\n)(.*)",
|
108 |
+
bygroups(Text, Operator, Text, using(PerlLexer)),
|
109 |
+
),
|
110 |
+
(
|
111 |
+
r"(?s)(\s*)(%%prun)([^\n]*\n)(.*)",
|
112 |
+
bygroups(Text, Operator, Text, using(Python3Lexer)),
|
113 |
+
),
|
114 |
+
(
|
115 |
+
r"(?s)(\s*)(%%pypy)([^\n]*\n)(.*)",
|
116 |
+
bygroups(Text, Operator, Text, using(Python3Lexer)),
|
117 |
+
),
|
118 |
+
(
|
119 |
+
r"(?s)(\s*)(%%python2)([^\n]*\n)(.*)",
|
120 |
+
bygroups(Text, Operator, Text, using(Python2Lexer)),
|
121 |
+
),
|
122 |
+
(
|
123 |
+
r"(?s)(\s*)(%%python3)([^\n]*\n)(.*)",
|
124 |
+
bygroups(Text, Operator, Text, using(Python3Lexer)),
|
125 |
+
),
|
126 |
+
(
|
127 |
+
r"(?s)(\s*)(%%python)([^\n]*\n)(.*)",
|
128 |
+
bygroups(Text, Operator, Text, using(Python3Lexer)),
|
129 |
+
),
|
130 |
+
(
|
131 |
+
r"(?s)(\s*)(%%ruby)([^\n]*\n)(.*)",
|
132 |
+
bygroups(Text, Operator, Text, using(RubyLexer)),
|
133 |
+
),
|
134 |
+
(
|
135 |
+
r"(?s)(\s*)(%%timeit)([^\n]*\n)(.*)",
|
136 |
+
bygroups(Text, Operator, Text, using(Python3Lexer)),
|
137 |
+
),
|
138 |
+
(
|
139 |
+
r"(?s)(\s*)(%%time)([^\n]*\n)(.*)",
|
140 |
+
bygroups(Text, Operator, Text, using(Python3Lexer)),
|
141 |
+
),
|
142 |
+
(
|
143 |
+
r"(?s)(\s*)(%%writefile)([^\n]*\n)(.*)",
|
144 |
+
bygroups(Text, Operator, Text, using(Python3Lexer)),
|
145 |
+
),
|
146 |
+
(
|
147 |
+
r"(?s)(\s*)(%%file)([^\n]*\n)(.*)",
|
148 |
+
bygroups(Text, Operator, Text, using(Python3Lexer)),
|
149 |
+
),
|
150 |
+
(r"(?s)(\s*)(%%)(\w+)(.*)", bygroups(Text, Operator, Keyword, Text)),
|
151 |
+
(
|
152 |
+
r"(?s)(^\s*)(%%!)([^\n]*\n)(.*)",
|
153 |
+
bygroups(Text, Operator, Text, using(BashLexer)),
|
154 |
+
),
|
155 |
+
(r"(%%?)(\w+)(\?\??)$", bygroups(Operator, Keyword, Operator)),
|
156 |
+
(r"\b(\?\??)(\s*)$", bygroups(Operator, Text)),
|
157 |
+
(r"(%)(sx|sc|system)(.*)(\n)", bygroups(Operator, Keyword, using(BashLexer), Text)),
|
158 |
+
(r"(%)(\w+)(.*\n)", bygroups(Operator, Keyword, Text)),
|
159 |
+
(r"^(!!)(.+)(\n)", bygroups(Operator, using(BashLexer), Text)),
|
160 |
+
(r"(!)(?!=)(.+)(\n)", bygroups(Operator, using(BashLexer), Text)),
|
161 |
+
(r"^(\s*)(\?\??)(\s*%{0,2}[\w\.\*]*)", bygroups(Text, Operator, Text)),
|
162 |
+
(r"(\s*%{0,2}[\w\.\*]*)(\?\??)(\s*)$", bygroups(Text, Operator, Text)),
|
163 |
+
]
|
164 |
+
|
165 |
+
|
166 |
+
class IPython3Lexer(Python3Lexer):
|
167 |
+
"""IPython code lexer (based on Python 3)"""
|
168 |
+
|
169 |
+
name = "IPython"
|
170 |
+
aliases = ["ipython", "ipython3"]
|
171 |
+
|
172 |
+
tokens = Python3Lexer.tokens.copy()
|
173 |
+
tokens["root"] = ipython_tokens + tokens["root"]
|
174 |
+
|
175 |
+
|
176 |
+
IPythonLexer = IPython3Lexer
|
177 |
+
|
178 |
+
|
179 |
+
class IPythonPartialTracebackLexer(RegexLexer):
|
180 |
+
"""
|
181 |
+
Partial lexer for IPython tracebacks.
|
182 |
+
|
183 |
+
Handles all the non-python output.
|
184 |
+
|
185 |
+
"""
|
186 |
+
|
187 |
+
name = "IPython Partial Traceback"
|
188 |
+
|
189 |
+
tokens = {
|
190 |
+
"root": [
|
191 |
+
# Tracebacks for syntax errors have a different style.
|
192 |
+
# For both types of tracebacks, we mark the first line with
|
193 |
+
# Generic.Traceback. For syntax errors, we mark the filename
|
194 |
+
# as we mark the filenames for non-syntax tracebacks.
|
195 |
+
#
|
196 |
+
# These two regexps define how IPythonConsoleLexer finds a
|
197 |
+
# traceback.
|
198 |
+
#
|
199 |
+
## Non-syntax traceback
|
200 |
+
(r"^(\^C)?(-+\n)", bygroups(Error, Generic.Traceback)),
|
201 |
+
## Syntax traceback
|
202 |
+
(
|
203 |
+
r"^( File)(.*)(, line )(\d+\n)",
|
204 |
+
bygroups(
|
205 |
+
Generic.Traceback,
|
206 |
+
Name.Namespace,
|
207 |
+
Generic.Traceback,
|
208 |
+
Literal.Number.Integer,
|
209 |
+
),
|
210 |
+
),
|
211 |
+
# (Exception Identifier)(Whitespace)(Traceback Message)
|
212 |
+
(
|
213 |
+
r"(?u)(^[^\d\W]\w*)(\s*)(Traceback.*?\n)",
|
214 |
+
bygroups(Name.Exception, Generic.Whitespace, Text),
|
215 |
+
),
|
216 |
+
# (Module/Filename)(Text)(Callee)(Function Signature)
|
217 |
+
# Better options for callee and function signature?
|
218 |
+
(
|
219 |
+
r"(.*)( in )(.*)(\(.*\)\n)",
|
220 |
+
bygroups(Name.Namespace, Text, Name.Entity, Name.Tag),
|
221 |
+
),
|
222 |
+
# Regular line: (Whitespace)(Line Number)(Python Code)
|
223 |
+
(
|
224 |
+
r"(\s*?)(\d+)(.*?\n)",
|
225 |
+
bygroups(Generic.Whitespace, Literal.Number.Integer, Other),
|
226 |
+
),
|
227 |
+
# Emphasized line: (Arrow)(Line Number)(Python Code)
|
228 |
+
# Using Exception token so arrow color matches the Exception.
|
229 |
+
(
|
230 |
+
r"(-*>?\s?)(\d+)(.*?\n)",
|
231 |
+
bygroups(Name.Exception, Literal.Number.Integer, Other),
|
232 |
+
),
|
233 |
+
# (Exception Identifier)(Message)
|
234 |
+
(r"(?u)(^[^\d\W]\w*)(:.*?\n)", bygroups(Name.Exception, Text)),
|
235 |
+
# Tag everything else as Other, will be handled later.
|
236 |
+
(r".*\n", Other),
|
237 |
+
],
|
238 |
+
}
|
239 |
+
|
240 |
+
|
241 |
+
class IPythonTracebackLexer(DelegatingLexer):
|
242 |
+
"""
|
243 |
+
IPython traceback lexer.
|
244 |
+
|
245 |
+
For doctests, the tracebacks can be snipped as much as desired with the
|
246 |
+
exception to the lines that designate a traceback. For non-syntax error
|
247 |
+
tracebacks, this is the line of hyphens. For syntax error tracebacks,
|
248 |
+
this is the line which lists the File and line number.
|
249 |
+
|
250 |
+
"""
|
251 |
+
|
252 |
+
# The lexer inherits from DelegatingLexer. The "root" lexer is an
|
253 |
+
# appropriate IPython lexer, which depends on the value of the boolean
|
254 |
+
# `python3`. First, we parse with the partial IPython traceback lexer.
|
255 |
+
# Then, any code marked with the "Other" token is delegated to the root
|
256 |
+
# lexer.
|
257 |
+
#
|
258 |
+
name = "IPython Traceback"
|
259 |
+
aliases = ["ipythontb", "ipython3tb"]
|
260 |
+
|
261 |
+
def __init__(self, **options):
|
262 |
+
"""
|
263 |
+
A subclass of `DelegatingLexer` which delegates to the appropriate to either IPyLexer,
|
264 |
+
IPythonPartialTracebackLexer.
|
265 |
+
"""
|
266 |
+
# note we need a __init__ doc, as otherwise it inherits the doc from the super class
|
267 |
+
# which will fail the documentation build as it references section of the pygments docs that
|
268 |
+
# do not exists when building IPython's docs.
|
269 |
+
DelegatingLexer.__init__(
|
270 |
+
self, IPython3Lexer, IPythonPartialTracebackLexer, **options
|
271 |
+
)
|
272 |
+
|
273 |
+
|
274 |
+
class IPythonConsoleLexer(Lexer):
|
275 |
+
"""
|
276 |
+
An IPython console lexer for IPython code-blocks and doctests, such as:
|
277 |
+
|
278 |
+
.. code-block:: rst
|
279 |
+
|
280 |
+
.. code-block:: ipythonconsole
|
281 |
+
|
282 |
+
In [1]: a = 'foo'
|
283 |
+
|
284 |
+
In [2]: a
|
285 |
+
Out[2]: 'foo'
|
286 |
+
|
287 |
+
In [3]: print(a)
|
288 |
+
foo
|
289 |
+
|
290 |
+
|
291 |
+
Support is also provided for IPython exceptions:
|
292 |
+
|
293 |
+
.. code-block:: rst
|
294 |
+
|
295 |
+
.. code-block:: ipythonconsole
|
296 |
+
|
297 |
+
In [1]: raise Exception
|
298 |
+
Traceback (most recent call last):
|
299 |
+
...
|
300 |
+
Exception
|
301 |
+
|
302 |
+
"""
|
303 |
+
|
304 |
+
name = "IPython console session"
|
305 |
+
aliases = ["ipythonconsole", "ipython3console"]
|
306 |
+
mimetypes = ["text/x-ipython-console"]
|
307 |
+
|
308 |
+
# The regexps used to determine what is input and what is output.
|
309 |
+
# The default prompts for IPython are:
|
310 |
+
#
|
311 |
+
# in = 'In [#]: '
|
312 |
+
# continuation = ' .D.: '
|
313 |
+
# template = 'Out[#]: '
|
314 |
+
#
|
315 |
+
# Where '#' is the 'prompt number' or 'execution count' and 'D'
|
316 |
+
# D is a number of dots matching the width of the execution count
|
317 |
+
#
|
318 |
+
in1_regex = r"In \[[0-9]+\]: "
|
319 |
+
in2_regex = r" \.\.+\.: "
|
320 |
+
out_regex = r"Out\[[0-9]+\]: "
|
321 |
+
|
322 |
+
#: The regex to determine when a traceback starts.
|
323 |
+
ipytb_start = re.compile(r"^(\^C)?(-+\n)|^( File)(.*)(, line )(\d+\n)")
|
324 |
+
|
325 |
+
def __init__(self, **options):
|
326 |
+
"""Initialize the IPython console lexer.
|
327 |
+
|
328 |
+
Parameters
|
329 |
+
----------
|
330 |
+
in1_regex : RegexObject
|
331 |
+
The compiled regular expression used to detect the start
|
332 |
+
of inputs. Although the IPython configuration setting may have a
|
333 |
+
trailing whitespace, do not include it in the regex. If `None`,
|
334 |
+
then the default input prompt is assumed.
|
335 |
+
in2_regex : RegexObject
|
336 |
+
The compiled regular expression used to detect the continuation
|
337 |
+
of inputs. Although the IPython configuration setting may have a
|
338 |
+
trailing whitespace, do not include it in the regex. If `None`,
|
339 |
+
then the default input prompt is assumed.
|
340 |
+
out_regex : RegexObject
|
341 |
+
The compiled regular expression used to detect outputs. If `None`,
|
342 |
+
then the default output prompt is assumed.
|
343 |
+
|
344 |
+
"""
|
345 |
+
in1_regex = options.get("in1_regex", self.in1_regex)
|
346 |
+
in2_regex = options.get("in2_regex", self.in2_regex)
|
347 |
+
out_regex = options.get("out_regex", self.out_regex)
|
348 |
+
|
349 |
+
# So that we can work with input and output prompts which have been
|
350 |
+
# rstrip'd (possibly by editors) we also need rstrip'd variants. If
|
351 |
+
# we do not do this, then such prompts will be tagged as 'output'.
|
352 |
+
# The reason can't just use the rstrip'd variants instead is because
|
353 |
+
# we want any whitespace associated with the prompt to be inserted
|
354 |
+
# with the token. This allows formatted code to be modified so as hide
|
355 |
+
# the appearance of prompts, with the whitespace included. One example
|
356 |
+
# use of this is in copybutton.js from the standard lib Python docs.
|
357 |
+
in1_regex_rstrip = in1_regex.rstrip() + "\n"
|
358 |
+
in2_regex_rstrip = in2_regex.rstrip() + "\n"
|
359 |
+
out_regex_rstrip = out_regex.rstrip() + "\n"
|
360 |
+
|
361 |
+
# Compile and save them all.
|
362 |
+
attrs = [
|
363 |
+
"in1_regex",
|
364 |
+
"in2_regex",
|
365 |
+
"out_regex",
|
366 |
+
"in1_regex_rstrip",
|
367 |
+
"in2_regex_rstrip",
|
368 |
+
"out_regex_rstrip",
|
369 |
+
]
|
370 |
+
for attr in attrs:
|
371 |
+
self.__setattr__(attr, re.compile(locals()[attr]))
|
372 |
+
|
373 |
+
Lexer.__init__(self, **options)
|
374 |
+
|
375 |
+
self.pylexer = IPython3Lexer(**options)
|
376 |
+
self.tblexer = IPythonTracebackLexer(**options)
|
377 |
+
|
378 |
+
self.reset()
|
379 |
+
|
380 |
+
def reset(self):
|
381 |
+
self.mode = "output"
|
382 |
+
self.index = 0
|
383 |
+
self.buffer = ""
|
384 |
+
self.insertions = []
|
385 |
+
|
386 |
+
def buffered_tokens(self):
|
387 |
+
"""
|
388 |
+
Generator of unprocessed tokens after doing insertions and before
|
389 |
+
changing to a new state.
|
390 |
+
|
391 |
+
"""
|
392 |
+
if self.mode == "output":
|
393 |
+
tokens = [(0, Generic.Output, self.buffer)]
|
394 |
+
elif self.mode == "input":
|
395 |
+
tokens = self.pylexer.get_tokens_unprocessed(self.buffer)
|
396 |
+
else: # traceback
|
397 |
+
tokens = self.tblexer.get_tokens_unprocessed(self.buffer)
|
398 |
+
|
399 |
+
for i, t, v in do_insertions(self.insertions, tokens):
|
400 |
+
# All token indexes are relative to the buffer.
|
401 |
+
yield self.index + i, t, v
|
402 |
+
|
403 |
+
# Clear it all
|
404 |
+
self.index += len(self.buffer)
|
405 |
+
self.buffer = ""
|
406 |
+
self.insertions = []
|
407 |
+
|
408 |
+
def get_mci(self, line):
|
409 |
+
"""
|
410 |
+
Parses the line and returns a 3-tuple: (mode, code, insertion).
|
411 |
+
|
412 |
+
`mode` is the next mode (or state) of the lexer, and is always equal
|
413 |
+
to 'input', 'output', or 'tb'.
|
414 |
+
|
415 |
+
`code` is a portion of the line that should be added to the buffer
|
416 |
+
corresponding to the next mode and eventually lexed by another lexer.
|
417 |
+
For example, `code` could be Python code if `mode` were 'input'.
|
418 |
+
|
419 |
+
`insertion` is a 3-tuple (index, token, text) representing an
|
420 |
+
unprocessed "token" that will be inserted into the stream of tokens
|
421 |
+
that are created from the buffer once we change modes. This is usually
|
422 |
+
the input or output prompt.
|
423 |
+
|
424 |
+
In general, the next mode depends on current mode and on the contents
|
425 |
+
of `line`.
|
426 |
+
|
427 |
+
"""
|
428 |
+
# To reduce the number of regex match checks, we have multiple
|
429 |
+
# 'if' blocks instead of 'if-elif' blocks.
|
430 |
+
|
431 |
+
# Check for possible end of input
|
432 |
+
in2_match = self.in2_regex.match(line)
|
433 |
+
in2_match_rstrip = self.in2_regex_rstrip.match(line)
|
434 |
+
if (
|
435 |
+
in2_match and in2_match.group().rstrip() == line.rstrip()
|
436 |
+
) or in2_match_rstrip:
|
437 |
+
end_input = True
|
438 |
+
else:
|
439 |
+
end_input = False
|
440 |
+
if end_input and self.mode != "tb":
|
441 |
+
# Only look for an end of input when not in tb mode.
|
442 |
+
# An ellipsis could appear within the traceback.
|
443 |
+
mode = "output"
|
444 |
+
code = ""
|
445 |
+
insertion = (0, Generic.Prompt, line)
|
446 |
+
return mode, code, insertion
|
447 |
+
|
448 |
+
# Check for output prompt
|
449 |
+
out_match = self.out_regex.match(line)
|
450 |
+
out_match_rstrip = self.out_regex_rstrip.match(line)
|
451 |
+
if out_match or out_match_rstrip:
|
452 |
+
mode = "output"
|
453 |
+
if out_match:
|
454 |
+
idx = out_match.end()
|
455 |
+
else:
|
456 |
+
idx = out_match_rstrip.end()
|
457 |
+
code = line[idx:]
|
458 |
+
# Use the 'heading' token for output. We cannot use Generic.Error
|
459 |
+
# since it would conflict with exceptions.
|
460 |
+
insertion = (0, Generic.Heading, line[:idx])
|
461 |
+
return mode, code, insertion
|
462 |
+
|
463 |
+
# Check for input or continuation prompt (non stripped version)
|
464 |
+
in1_match = self.in1_regex.match(line)
|
465 |
+
if in1_match or (in2_match and self.mode != "tb"):
|
466 |
+
# New input or when not in tb, continued input.
|
467 |
+
# We do not check for continued input when in tb since it is
|
468 |
+
# allowable to replace a long stack with an ellipsis.
|
469 |
+
mode = "input"
|
470 |
+
if in1_match:
|
471 |
+
idx = in1_match.end()
|
472 |
+
else: # in2_match
|
473 |
+
idx = in2_match.end()
|
474 |
+
code = line[idx:]
|
475 |
+
insertion = (0, Generic.Prompt, line[:idx])
|
476 |
+
return mode, code, insertion
|
477 |
+
|
478 |
+
# Check for input or continuation prompt (stripped version)
|
479 |
+
in1_match_rstrip = self.in1_regex_rstrip.match(line)
|
480 |
+
if in1_match_rstrip or (in2_match_rstrip and self.mode != "tb"):
|
481 |
+
# New input or when not in tb, continued input.
|
482 |
+
# We do not check for continued input when in tb since it is
|
483 |
+
# allowable to replace a long stack with an ellipsis.
|
484 |
+
mode = "input"
|
485 |
+
if in1_match_rstrip:
|
486 |
+
idx = in1_match_rstrip.end()
|
487 |
+
else: # in2_match
|
488 |
+
idx = in2_match_rstrip.end()
|
489 |
+
code = line[idx:]
|
490 |
+
insertion = (0, Generic.Prompt, line[:idx])
|
491 |
+
return mode, code, insertion
|
492 |
+
|
493 |
+
# Check for traceback
|
494 |
+
if self.ipytb_start.match(line):
|
495 |
+
mode = "tb"
|
496 |
+
code = line
|
497 |
+
insertion = None
|
498 |
+
return mode, code, insertion
|
499 |
+
|
500 |
+
# All other stuff...
|
501 |
+
if self.mode in ("input", "output"):
|
502 |
+
# We assume all other text is output. Multiline input that
|
503 |
+
# does not use the continuation marker cannot be detected.
|
504 |
+
# For example, the 3 in the following is clearly output:
|
505 |
+
#
|
506 |
+
# In [1]: print(3)
|
507 |
+
# 3
|
508 |
+
#
|
509 |
+
# But the following second line is part of the input:
|
510 |
+
#
|
511 |
+
# In [2]: while True:
|
512 |
+
# print(True)
|
513 |
+
#
|
514 |
+
# In both cases, the 2nd line will be 'output'.
|
515 |
+
#
|
516 |
+
mode = "output"
|
517 |
+
else:
|
518 |
+
mode = "tb"
|
519 |
+
|
520 |
+
code = line
|
521 |
+
insertion = None
|
522 |
+
|
523 |
+
return mode, code, insertion
|
524 |
+
|
525 |
+
def get_tokens_unprocessed(self, text):
|
526 |
+
self.reset()
|
527 |
+
for match in line_re.finditer(text):
|
528 |
+
line = match.group()
|
529 |
+
mode, code, insertion = self.get_mci(line)
|
530 |
+
|
531 |
+
if mode != self.mode:
|
532 |
+
# Yield buffered tokens before transitioning to new mode.
|
533 |
+
for token in self.buffered_tokens():
|
534 |
+
yield token
|
535 |
+
self.mode = mode
|
536 |
+
|
537 |
+
if insertion:
|
538 |
+
self.insertions.append((len(self.buffer), [insertion]))
|
539 |
+
self.buffer += code
|
540 |
+
|
541 |
+
for token in self.buffered_tokens():
|
542 |
+
yield token
|
543 |
+
|
544 |
+
|
545 |
+
class IPyLexer(Lexer):
|
546 |
+
r"""
|
547 |
+
Primary lexer for all IPython-like code.
|
548 |
+
|
549 |
+
This is a simple helper lexer. If the first line of the text begins with
|
550 |
+
"In \[[0-9]+\]:", then the entire text is parsed with an IPython console
|
551 |
+
lexer. If not, then the entire text is parsed with an IPython lexer.
|
552 |
+
|
553 |
+
The goal is to reduce the number of lexers that are registered
|
554 |
+
with Pygments.
|
555 |
+
|
556 |
+
"""
|
557 |
+
|
558 |
+
name = "IPy session"
|
559 |
+
aliases = ["ipy", "ipy3"]
|
560 |
+
|
561 |
+
def __init__(self, **options):
|
562 |
+
"""
|
563 |
+
Create a new IPyLexer instance which dispatch to either an
|
564 |
+
IPythonCOnsoleLexer (if In prompts are present) or and IPythonLexer (if
|
565 |
+
In prompts are not present).
|
566 |
+
"""
|
567 |
+
# init docstring is necessary for docs not to fail to build do to parent
|
568 |
+
# docs referenceing a section in pygments docs.
|
569 |
+
Lexer.__init__(self, **options)
|
570 |
+
|
571 |
+
self.IPythonLexer = IPythonLexer(**options)
|
572 |
+
self.IPythonConsoleLexer = IPythonConsoleLexer(**options)
|
573 |
+
|
574 |
+
def get_tokens_unprocessed(self, text):
|
575 |
+
# Search for the input prompt anywhere...this allows code blocks to
|
576 |
+
# begin with comments as well.
|
577 |
+
if re.match(r".*(In \[[0-9]+\]:)", text.strip(), re.DOTALL):
|
578 |
+
lex = self.IPythonConsoleLexer
|
579 |
+
else:
|
580 |
+
lex = self.IPythonLexer
|
581 |
+
for token in lex.get_tokens_unprocessed(text):
|
582 |
+
yield token
|
venv/Lib/site-packages/isympy.py
ADDED
@@ -0,0 +1,342 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
"""
|
2 |
+
Python shell for SymPy.
|
3 |
+
|
4 |
+
This is just a normal Python shell (IPython shell if you have the
|
5 |
+
IPython package installed), that executes the following commands for
|
6 |
+
the user:
|
7 |
+
|
8 |
+
>>> from __future__ import division
|
9 |
+
>>> from sympy import *
|
10 |
+
>>> x, y, z, t = symbols('x y z t')
|
11 |
+
>>> k, m, n = symbols('k m n', integer=True)
|
12 |
+
>>> f, g, h = symbols('f g h', cls=Function)
|
13 |
+
>>> init_printing()
|
14 |
+
|
15 |
+
So starting 'isympy' is equivalent to starting Python (or IPython) and
|
16 |
+
executing the above commands by hand. It is intended for easy and quick
|
17 |
+
experimentation with SymPy. isympy is a good way to use SymPy as an
|
18 |
+
interactive calculator. If you have IPython and Matplotlib installed, then
|
19 |
+
interactive plotting is enabled by default.
|
20 |
+
|
21 |
+
COMMAND LINE OPTIONS
|
22 |
+
--------------------
|
23 |
+
|
24 |
+
-c CONSOLE, --console=CONSOLE
|
25 |
+
|
26 |
+
Use the specified shell (Python or IPython) shell as the console
|
27 |
+
backend instead of the default one (IPython if present, Python
|
28 |
+
otherwise), e.g.:
|
29 |
+
|
30 |
+
$isympy -c python
|
31 |
+
|
32 |
+
CONSOLE must be one of 'ipython' or 'python'
|
33 |
+
|
34 |
+
-p PRETTY, --pretty PRETTY
|
35 |
+
|
36 |
+
Setup pretty-printing in SymPy. When pretty-printing is enabled,
|
37 |
+
expressions can be printed with Unicode or ASCII. The default is
|
38 |
+
to use pretty-printing (with Unicode if the terminal supports it).
|
39 |
+
When this option is 'no', expressions will not be pretty-printed
|
40 |
+
and ASCII will be used:
|
41 |
+
|
42 |
+
$isympy -p no
|
43 |
+
|
44 |
+
PRETTY must be one of 'unicode', 'ascii', or 'no'
|
45 |
+
|
46 |
+
-t TYPES, --types=TYPES
|
47 |
+
|
48 |
+
Setup the ground types for the polys. By default, gmpy ground types
|
49 |
+
are used if gmpy2 or gmpy is installed, otherwise it falls back to python
|
50 |
+
ground types, which are a little bit slower. You can manually
|
51 |
+
choose python ground types even if gmpy is installed (e.g., for
|
52 |
+
testing purposes):
|
53 |
+
|
54 |
+
$isympy -t python
|
55 |
+
|
56 |
+
TYPES must be one of 'gmpy', 'gmpy1' or 'python'
|
57 |
+
|
58 |
+
Note that the ground type gmpy1 is primarily intended for testing; it
|
59 |
+
forces the use of gmpy version 1 even if gmpy2 is available.
|
60 |
+
|
61 |
+
This is the same as setting the environment variable
|
62 |
+
SYMPY_GROUND_TYPES to the given ground type (e.g.,
|
63 |
+
SYMPY_GROUND_TYPES='gmpy')
|
64 |
+
|
65 |
+
The ground types can be determined interactively from the variable
|
66 |
+
sympy.polys.domains.GROUND_TYPES.
|
67 |
+
|
68 |
+
-o ORDER, --order ORDER
|
69 |
+
|
70 |
+
Setup the ordering of terms for printing. The default is lex, which
|
71 |
+
orders terms lexicographically (e.g., x**2 + x + 1). You can choose
|
72 |
+
other orderings, such as rev-lex, which will use reverse
|
73 |
+
lexicographic ordering (e.g., 1 + x + x**2):
|
74 |
+
|
75 |
+
$isympy -o rev-lex
|
76 |
+
|
77 |
+
ORDER must be one of 'lex', 'rev-lex', 'grlex', 'rev-grlex',
|
78 |
+
'grevlex', 'rev-grevlex', 'old', or 'none'.
|
79 |
+
|
80 |
+
Note that for very large expressions, ORDER='none' may speed up
|
81 |
+
printing considerably but the terms will have no canonical order.
|
82 |
+
|
83 |
+
-q, --quiet
|
84 |
+
|
85 |
+
Print only Python's and SymPy's versions to stdout at startup.
|
86 |
+
|
87 |
+
-d, --doctest
|
88 |
+
|
89 |
+
Use the same format that should be used for doctests. This is
|
90 |
+
equivalent to -c python -p no.
|
91 |
+
|
92 |
+
-C, --no-cache
|
93 |
+
|
94 |
+
Disable the caching mechanism. Disabling the cache may slow certain
|
95 |
+
operations down considerably. This is useful for testing the cache,
|
96 |
+
or for benchmarking, as the cache can result in deceptive timings.
|
97 |
+
|
98 |
+
This is equivalent to setting the environment variable
|
99 |
+
SYMPY_USE_CACHE to 'no'.
|
100 |
+
|
101 |
+
-a, --auto-symbols (requires at least IPython 0.11)
|
102 |
+
|
103 |
+
Automatically create missing symbols. Normally, typing a name of a
|
104 |
+
Symbol that has not been instantiated first would raise NameError,
|
105 |
+
but with this option enabled, any undefined name will be
|
106 |
+
automatically created as a Symbol.
|
107 |
+
|
108 |
+
Note that this is intended only for interactive, calculator style
|
109 |
+
usage. In a script that uses SymPy, Symbols should be instantiated
|
110 |
+
at the top, so that it's clear what they are.
|
111 |
+
|
112 |
+
This will not override any names that are already defined, which
|
113 |
+
includes the single character letters represented by the mnemonic
|
114 |
+
QCOSINE (see the "Gotchas and Pitfalls" document in the
|
115 |
+
documentation). You can delete existing names by executing "del
|
116 |
+
name". If a name is defined, typing "'name' in dir()" will return True.
|
117 |
+
|
118 |
+
The Symbols that are created using this have default assumptions.
|
119 |
+
If you want to place assumptions on symbols, you should create them
|
120 |
+
using symbols() or var().
|
121 |
+
|
122 |
+
Finally, this only works in the top level namespace. So, for
|
123 |
+
example, if you define a function in isympy with an undefined
|
124 |
+
Symbol, it will not work.
|
125 |
+
|
126 |
+
See also the -i and -I options.
|
127 |
+
|
128 |
+
-i, --int-to-Integer (requires at least IPython 0.11)
|
129 |
+
|
130 |
+
Automatically wrap int literals with Integer. This makes it so that
|
131 |
+
things like 1/2 will come out as Rational(1, 2), rather than 0.5. This
|
132 |
+
works by preprocessing the source and wrapping all int literals with
|
133 |
+
Integer. Note that this will not change the behavior of int literals
|
134 |
+
assigned to variables, and it also won't change the behavior of functions
|
135 |
+
that return int literals.
|
136 |
+
|
137 |
+
If you want an int, you can wrap the literal in int(), e.g. int(3)/int(2)
|
138 |
+
gives 1.5 (with division imported from __future__).
|
139 |
+
|
140 |
+
-I, --interactive (requires at least IPython 0.11)
|
141 |
+
|
142 |
+
This is equivalent to --auto-symbols --int-to-Integer. Future options
|
143 |
+
designed for ease of interactive use may be added to this.
|
144 |
+
|
145 |
+
-D, --debug
|
146 |
+
|
147 |
+
Enable debugging output. This is the same as setting the
|
148 |
+
environment variable SYMPY_DEBUG to 'True'. The debug status is set
|
149 |
+
in the variable SYMPY_DEBUG within isympy.
|
150 |
+
|
151 |
+
-- IPython options
|
152 |
+
|
153 |
+
Additionally you can pass command line options directly to the IPython
|
154 |
+
interpreter (the standard Python shell is not supported). However you
|
155 |
+
need to add the '--' separator between two types of options, e.g the
|
156 |
+
startup banner option and the colors option. You need to enter the
|
157 |
+
options as required by the version of IPython that you are using, too:
|
158 |
+
|
159 |
+
in IPython 0.11,
|
160 |
+
|
161 |
+
$isympy -q -- --colors=NoColor
|
162 |
+
|
163 |
+
or older versions of IPython,
|
164 |
+
|
165 |
+
$isympy -q -- -colors NoColor
|
166 |
+
|
167 |
+
See also isympy --help.
|
168 |
+
"""
|
169 |
+
|
170 |
+
import os
|
171 |
+
import sys
|
172 |
+
|
173 |
+
# DO NOT IMPORT SYMPY HERE! Or the setting of the sympy environment variables
|
174 |
+
# by the command line will break.
|
175 |
+
|
176 |
+
def main() -> None:
|
177 |
+
from argparse import ArgumentParser, RawDescriptionHelpFormatter
|
178 |
+
|
179 |
+
VERSION = None
|
180 |
+
if '--version' in sys.argv:
|
181 |
+
# We cannot import sympy before this is run, because flags like -C and
|
182 |
+
# -t set environment variables that must be set before SymPy is
|
183 |
+
# imported. The only thing we need to import it for is to get the
|
184 |
+
# version, which only matters with the --version flag.
|
185 |
+
import sympy
|
186 |
+
VERSION = sympy.__version__
|
187 |
+
|
188 |
+
usage = 'isympy [options] -- [ipython options]'
|
189 |
+
parser = ArgumentParser(
|
190 |
+
usage=usage,
|
191 |
+
description=__doc__,
|
192 |
+
formatter_class=RawDescriptionHelpFormatter,
|
193 |
+
)
|
194 |
+
|
195 |
+
parser.add_argument('--version', action='version', version=VERSION)
|
196 |
+
|
197 |
+
parser.add_argument(
|
198 |
+
'-c', '--console',
|
199 |
+
dest='console',
|
200 |
+
action='store',
|
201 |
+
default=None,
|
202 |
+
choices=['ipython', 'python'],
|
203 |
+
metavar='CONSOLE',
|
204 |
+
help='select type of interactive session: ipython | python; defaults '
|
205 |
+
'to ipython if IPython is installed, otherwise python')
|
206 |
+
|
207 |
+
parser.add_argument(
|
208 |
+
'-p', '--pretty',
|
209 |
+
dest='pretty',
|
210 |
+
action='store',
|
211 |
+
default=None,
|
212 |
+
metavar='PRETTY',
|
213 |
+
choices=['unicode', 'ascii', 'no'],
|
214 |
+
help='setup pretty printing: unicode | ascii | no; defaults to '
|
215 |
+
'unicode printing if the terminal supports it, otherwise ascii')
|
216 |
+
|
217 |
+
parser.add_argument(
|
218 |
+
'-t', '--types',
|
219 |
+
dest='types',
|
220 |
+
action='store',
|
221 |
+
default=None,
|
222 |
+
metavar='TYPES',
|
223 |
+
choices=['gmpy', 'gmpy1', 'python'],
|
224 |
+
help='setup ground types: gmpy | gmpy1 | python; defaults to gmpy if gmpy2 '
|
225 |
+
'or gmpy is installed, otherwise python')
|
226 |
+
|
227 |
+
parser.add_argument(
|
228 |
+
'-o', '--order',
|
229 |
+
dest='order',
|
230 |
+
action='store',
|
231 |
+
default=None,
|
232 |
+
metavar='ORDER',
|
233 |
+
choices=['lex', 'grlex', 'grevlex', 'rev-lex', 'rev-grlex', 'rev-grevlex', 'old', 'none'],
|
234 |
+
help='setup ordering of terms: [rev-]lex | [rev-]grlex | [rev-]grevlex | old | none; defaults to lex')
|
235 |
+
|
236 |
+
parser.add_argument(
|
237 |
+
'-q', '--quiet',
|
238 |
+
dest='quiet',
|
239 |
+
action='store_true',
|
240 |
+
default=False,
|
241 |
+
help='print only version information at startup')
|
242 |
+
|
243 |
+
parser.add_argument(
|
244 |
+
'-d', '--doctest',
|
245 |
+
dest='doctest',
|
246 |
+
action='store_true',
|
247 |
+
default=False,
|
248 |
+
help='use the doctest format for output (you can just copy and paste it)')
|
249 |
+
|
250 |
+
parser.add_argument(
|
251 |
+
'-C', '--no-cache',
|
252 |
+
dest='cache',
|
253 |
+
action='store_false',
|
254 |
+
default=True,
|
255 |
+
help='disable caching mechanism')
|
256 |
+
|
257 |
+
parser.add_argument(
|
258 |
+
'-a', '--auto-symbols',
|
259 |
+
dest='auto_symbols',
|
260 |
+
action='store_true',
|
261 |
+
default=False,
|
262 |
+
help='automatically construct missing symbols')
|
263 |
+
|
264 |
+
parser.add_argument(
|
265 |
+
'-i', '--int-to-Integer',
|
266 |
+
dest='auto_int_to_Integer',
|
267 |
+
action='store_true',
|
268 |
+
default=False,
|
269 |
+
help="automatically wrap int literals with Integer")
|
270 |
+
|
271 |
+
parser.add_argument(
|
272 |
+
'-I', '--interactive',
|
273 |
+
dest='interactive',
|
274 |
+
action='store_true',
|
275 |
+
default=False,
|
276 |
+
help="equivalent to -a -i")
|
277 |
+
|
278 |
+
parser.add_argument(
|
279 |
+
'-D', '--debug',
|
280 |
+
dest='debug',
|
281 |
+
action='store_true',
|
282 |
+
default=False,
|
283 |
+
help='enable debugging output')
|
284 |
+
|
285 |
+
(options, ipy_args) = parser.parse_known_args()
|
286 |
+
if '--' in ipy_args:
|
287 |
+
ipy_args.remove('--')
|
288 |
+
|
289 |
+
if not options.cache:
|
290 |
+
os.environ['SYMPY_USE_CACHE'] = 'no'
|
291 |
+
|
292 |
+
if options.types:
|
293 |
+
os.environ['SYMPY_GROUND_TYPES'] = options.types
|
294 |
+
|
295 |
+
if options.debug:
|
296 |
+
os.environ['SYMPY_DEBUG'] = str(options.debug)
|
297 |
+
|
298 |
+
if options.doctest:
|
299 |
+
options.pretty = 'no'
|
300 |
+
options.console = 'python'
|
301 |
+
|
302 |
+
session = options.console
|
303 |
+
|
304 |
+
if session is not None:
|
305 |
+
ipython = session == 'ipython'
|
306 |
+
else:
|
307 |
+
try:
|
308 |
+
import IPython # noqa: F401
|
309 |
+
ipython = True
|
310 |
+
except ImportError:
|
311 |
+
if not options.quiet:
|
312 |
+
from sympy.interactive.session import no_ipython
|
313 |
+
print(no_ipython)
|
314 |
+
ipython = False
|
315 |
+
|
316 |
+
args = {
|
317 |
+
'pretty_print': True,
|
318 |
+
'use_unicode': None,
|
319 |
+
'use_latex': None,
|
320 |
+
'order': None,
|
321 |
+
'argv': ipy_args,
|
322 |
+
}
|
323 |
+
|
324 |
+
if options.pretty == 'unicode':
|
325 |
+
args['use_unicode'] = True
|
326 |
+
elif options.pretty == 'ascii':
|
327 |
+
args['use_unicode'] = False
|
328 |
+
elif options.pretty == 'no':
|
329 |
+
args['pretty_print'] = False
|
330 |
+
|
331 |
+
if options.order is not None:
|
332 |
+
args['order'] = options.order
|
333 |
+
|
334 |
+
args['quiet'] = options.quiet
|
335 |
+
args['auto_symbols'] = options.auto_symbols or options.interactive
|
336 |
+
args['auto_int_to_Integer'] = options.auto_int_to_Integer or options.interactive
|
337 |
+
|
338 |
+
from sympy.interactive import init_session
|
339 |
+
init_session(ipython, **args)
|
340 |
+
|
341 |
+
if __name__ == "__main__":
|
342 |
+
main()
|
venv/Lib/site-packages/jsonpointer.py
ADDED
@@ -0,0 +1,348 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
# -*- coding: utf-8 -*-
|
2 |
+
#
|
3 |
+
# python-json-pointer - An implementation of the JSON Pointer syntax
|
4 |
+
# https://github.com/stefankoegl/python-json-pointer
|
5 |
+
#
|
6 |
+
# Copyright (c) 2011 Stefan Kögl <[email protected]>
|
7 |
+
# All rights reserved.
|
8 |
+
#
|
9 |
+
# Redistribution and use in source and binary forms, with or without
|
10 |
+
# modification, are permitted provided that the following conditions
|
11 |
+
# are met:
|
12 |
+
#
|
13 |
+
# 1. Redistributions of source code must retain the above copyright
|
14 |
+
# notice, this list of conditions and the following disclaimer.
|
15 |
+
# 2. Redistributions in binary form must reproduce the above copyright
|
16 |
+
# notice, this list of conditions and the following disclaimer in the
|
17 |
+
# documentation and/or other materials provided with the distribution.
|
18 |
+
# 3. The name of the author may not be used to endorse or promote products
|
19 |
+
# derived from this software without specific prior written permission.
|
20 |
+
#
|
21 |
+
# THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
|
22 |
+
# IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
23 |
+
# OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
24 |
+
# IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
|
25 |
+
# INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
26 |
+
# NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
27 |
+
# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
28 |
+
# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
29 |
+
# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
30 |
+
# THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
31 |
+
#
|
32 |
+
|
33 |
+
""" Identify specific nodes in a JSON document (RFC 6901) """
|
34 |
+
|
35 |
+
# Will be parsed by setup.py to determine package metadata
|
36 |
+
__author__ = 'Stefan Kögl <[email protected]>'
|
37 |
+
__version__ = '3.0.0'
|
38 |
+
__website__ = 'https://github.com/stefankoegl/python-json-pointer'
|
39 |
+
__license__ = 'Modified BSD License'
|
40 |
+
|
41 |
+
import copy
|
42 |
+
import re
|
43 |
+
from collections.abc import Mapping, Sequence
|
44 |
+
from itertools import tee, chain
|
45 |
+
|
46 |
+
_nothing = object()
|
47 |
+
|
48 |
+
|
49 |
+
def set_pointer(doc, pointer, value, inplace=True):
|
50 |
+
"""Resolves a pointer against doc and sets the value of the target within doc.
|
51 |
+
|
52 |
+
With inplace set to true, doc is modified as long as pointer is not the
|
53 |
+
root.
|
54 |
+
|
55 |
+
>>> obj = {'foo': {'anArray': [ {'prop': 44}], 'another prop': {'baz': 'A string' }}}
|
56 |
+
|
57 |
+
>>> set_pointer(obj, '/foo/anArray/0/prop', 55) == \
|
58 |
+
{'foo': {'another prop': {'baz': 'A string'}, 'anArray': [{'prop': 55}]}}
|
59 |
+
True
|
60 |
+
|
61 |
+
>>> set_pointer(obj, '/foo/yet another prop', 'added prop') == \
|
62 |
+
{'foo': {'another prop': {'baz': 'A string'}, 'yet another prop': 'added prop', 'anArray': [{'prop': 55}]}}
|
63 |
+
True
|
64 |
+
|
65 |
+
>>> obj = {'foo': {}}
|
66 |
+
>>> set_pointer(obj, '/foo/a%20b', 'x') == \
|
67 |
+
{'foo': {'a%20b': 'x' }}
|
68 |
+
True
|
69 |
+
"""
|
70 |
+
|
71 |
+
pointer = JsonPointer(pointer)
|
72 |
+
return pointer.set(doc, value, inplace)
|
73 |
+
|
74 |
+
|
75 |
+
def resolve_pointer(doc, pointer, default=_nothing):
|
76 |
+
""" Resolves pointer against doc and returns the referenced object
|
77 |
+
|
78 |
+
>>> obj = {'foo': {'anArray': [ {'prop': 44}], 'another prop': {'baz': 'A string' }}, 'a%20b': 1, 'c d': 2}
|
79 |
+
|
80 |
+
>>> resolve_pointer(obj, '') == obj
|
81 |
+
True
|
82 |
+
|
83 |
+
>>> resolve_pointer(obj, '/foo') == obj['foo']
|
84 |
+
True
|
85 |
+
|
86 |
+
>>> resolve_pointer(obj, '/foo/another prop') == obj['foo']['another prop']
|
87 |
+
True
|
88 |
+
|
89 |
+
>>> resolve_pointer(obj, '/foo/another prop/baz') == obj['foo']['another prop']['baz']
|
90 |
+
True
|
91 |
+
|
92 |
+
>>> resolve_pointer(obj, '/foo/anArray/0') == obj['foo']['anArray'][0]
|
93 |
+
True
|
94 |
+
|
95 |
+
>>> resolve_pointer(obj, '/some/path', None) == None
|
96 |
+
True
|
97 |
+
|
98 |
+
>>> resolve_pointer(obj, '/a b', None) == None
|
99 |
+
True
|
100 |
+
|
101 |
+
>>> resolve_pointer(obj, '/a%20b') == 1
|
102 |
+
True
|
103 |
+
|
104 |
+
>>> resolve_pointer(obj, '/c d') == 2
|
105 |
+
True
|
106 |
+
|
107 |
+
>>> resolve_pointer(obj, '/c%20d', None) == None
|
108 |
+
True
|
109 |
+
"""
|
110 |
+
|
111 |
+
pointer = JsonPointer(pointer)
|
112 |
+
return pointer.resolve(doc, default)
|
113 |
+
|
114 |
+
|
115 |
+
def pairwise(iterable):
|
116 |
+
""" Transforms a list to a list of tuples of adjacent items
|
117 |
+
|
118 |
+
s -> (s0,s1), (s1,s2), (s2, s3), ...
|
119 |
+
|
120 |
+
>>> list(pairwise([]))
|
121 |
+
[]
|
122 |
+
|
123 |
+
>>> list(pairwise([1]))
|
124 |
+
[]
|
125 |
+
|
126 |
+
>>> list(pairwise([1, 2, 3, 4]))
|
127 |
+
[(1, 2), (2, 3), (3, 4)]
|
128 |
+
"""
|
129 |
+
a, b = tee(iterable)
|
130 |
+
for _ in b:
|
131 |
+
break
|
132 |
+
return zip(a, b)
|
133 |
+
|
134 |
+
|
135 |
+
class JsonPointerException(Exception):
|
136 |
+
pass
|
137 |
+
|
138 |
+
|
139 |
+
class EndOfList(object):
|
140 |
+
"""Result of accessing element "-" of a list"""
|
141 |
+
|
142 |
+
def __init__(self, list_):
|
143 |
+
self.list_ = list_
|
144 |
+
|
145 |
+
def __repr__(self):
|
146 |
+
return '{cls}({lst})'.format(cls=self.__class__.__name__,
|
147 |
+
lst=repr(self.list_))
|
148 |
+
|
149 |
+
|
150 |
+
class JsonPointer(object):
|
151 |
+
"""A JSON Pointer that can reference parts of a JSON document"""
|
152 |
+
|
153 |
+
# Array indices must not contain:
|
154 |
+
# leading zeros, signs, spaces, decimals, etc
|
155 |
+
_RE_ARRAY_INDEX = re.compile('0|[1-9][0-9]*$')
|
156 |
+
_RE_INVALID_ESCAPE = re.compile('(~[^01]|~$)')
|
157 |
+
|
158 |
+
def __init__(self, pointer):
|
159 |
+
|
160 |
+
# validate escapes
|
161 |
+
invalid_escape = self._RE_INVALID_ESCAPE.search(pointer)
|
162 |
+
if invalid_escape:
|
163 |
+
raise JsonPointerException('Found invalid escape {}'.format(
|
164 |
+
invalid_escape.group()))
|
165 |
+
|
166 |
+
parts = pointer.split('/')
|
167 |
+
if parts.pop(0) != '':
|
168 |
+
raise JsonPointerException('Location must start with /')
|
169 |
+
|
170 |
+
parts = [unescape(part) for part in parts]
|
171 |
+
self.parts = parts
|
172 |
+
|
173 |
+
def to_last(self, doc):
|
174 |
+
"""Resolves ptr until the last step, returns (sub-doc, last-step)"""
|
175 |
+
|
176 |
+
if not self.parts:
|
177 |
+
return doc, None
|
178 |
+
|
179 |
+
for part in self.parts[:-1]:
|
180 |
+
doc = self.walk(doc, part)
|
181 |
+
|
182 |
+
return doc, JsonPointer.get_part(doc, self.parts[-1])
|
183 |
+
|
184 |
+
def resolve(self, doc, default=_nothing):
|
185 |
+
"""Resolves the pointer against doc and returns the referenced object"""
|
186 |
+
|
187 |
+
for part in self.parts:
|
188 |
+
|
189 |
+
try:
|
190 |
+
doc = self.walk(doc, part)
|
191 |
+
except JsonPointerException:
|
192 |
+
if default is _nothing:
|
193 |
+
raise
|
194 |
+
else:
|
195 |
+
return default
|
196 |
+
|
197 |
+
return doc
|
198 |
+
|
199 |
+
get = resolve
|
200 |
+
|
201 |
+
def set(self, doc, value, inplace=True):
|
202 |
+
"""Resolve the pointer against the doc and replace the target with value."""
|
203 |
+
|
204 |
+
if len(self.parts) == 0:
|
205 |
+
if inplace:
|
206 |
+
raise JsonPointerException('Cannot set root in place')
|
207 |
+
return value
|
208 |
+
|
209 |
+
if not inplace:
|
210 |
+
doc = copy.deepcopy(doc)
|
211 |
+
|
212 |
+
(parent, part) = self.to_last(doc)
|
213 |
+
|
214 |
+
if isinstance(parent, Sequence) and part == '-':
|
215 |
+
parent.append(value)
|
216 |
+
else:
|
217 |
+
parent[part] = value
|
218 |
+
|
219 |
+
return doc
|
220 |
+
|
221 |
+
@classmethod
|
222 |
+
def get_part(cls, doc, part):
|
223 |
+
"""Returns the next step in the correct type"""
|
224 |
+
|
225 |
+
if isinstance(doc, Mapping):
|
226 |
+
return part
|
227 |
+
|
228 |
+
elif isinstance(doc, Sequence):
|
229 |
+
|
230 |
+
if part == '-':
|
231 |
+
return part
|
232 |
+
|
233 |
+
if not JsonPointer._RE_ARRAY_INDEX.match(str(part)):
|
234 |
+
raise JsonPointerException("'%s' is not a valid sequence index" % part)
|
235 |
+
|
236 |
+
return int(part)
|
237 |
+
|
238 |
+
elif hasattr(doc, '__getitem__'):
|
239 |
+
# Allow indexing via ducktyping
|
240 |
+
# if the target has defined __getitem__
|
241 |
+
return part
|
242 |
+
|
243 |
+
else:
|
244 |
+
raise JsonPointerException("Document '%s' does not support indexing, "
|
245 |
+
"must be mapping/sequence or support __getitem__" % type(doc))
|
246 |
+
|
247 |
+
def get_parts(self):
|
248 |
+
"""Returns the list of the parts. For example, JsonPointer('/a/b').get_parts() == ['a', 'b']"""
|
249 |
+
|
250 |
+
return self.parts
|
251 |
+
|
252 |
+
def walk(self, doc, part):
|
253 |
+
""" Walks one step in doc and returns the referenced part """
|
254 |
+
|
255 |
+
part = JsonPointer.get_part(doc, part)
|
256 |
+
|
257 |
+
assert hasattr(doc, '__getitem__'), "invalid document type %s" % (type(doc),)
|
258 |
+
|
259 |
+
if isinstance(doc, Sequence):
|
260 |
+
if part == '-':
|
261 |
+
return EndOfList(doc)
|
262 |
+
|
263 |
+
try:
|
264 |
+
return doc[part]
|
265 |
+
|
266 |
+
except IndexError:
|
267 |
+
raise JsonPointerException("index '%s' is out of bounds" % (part,))
|
268 |
+
|
269 |
+
# Else the object is a mapping or supports __getitem__(so assume custom indexing)
|
270 |
+
try:
|
271 |
+
return doc[part]
|
272 |
+
|
273 |
+
except KeyError:
|
274 |
+
raise JsonPointerException("member '%s' not found in %s" % (part, doc))
|
275 |
+
|
276 |
+
def contains(self, ptr):
|
277 |
+
""" Returns True if self contains the given ptr """
|
278 |
+
return self.parts[:len(ptr.parts)] == ptr.parts
|
279 |
+
|
280 |
+
def __contains__(self, item):
|
281 |
+
""" Returns True if self contains the given ptr """
|
282 |
+
return self.contains(item)
|
283 |
+
|
284 |
+
def join(self, suffix):
|
285 |
+
""" Returns a new JsonPointer with the given suffix append to this ptr """
|
286 |
+
if isinstance(suffix, JsonPointer):
|
287 |
+
suffix_parts = suffix.parts
|
288 |
+
elif isinstance(suffix, str):
|
289 |
+
suffix_parts = JsonPointer(suffix).parts
|
290 |
+
else:
|
291 |
+
suffix_parts = suffix
|
292 |
+
try:
|
293 |
+
return JsonPointer.from_parts(chain(self.parts, suffix_parts))
|
294 |
+
except: # noqa E722
|
295 |
+
raise JsonPointerException("Invalid suffix")
|
296 |
+
|
297 |
+
def __truediv__(self, suffix): # Python 3
|
298 |
+
return self.join(suffix)
|
299 |
+
|
300 |
+
@property
|
301 |
+
def path(self):
|
302 |
+
"""Returns the string representation of the pointer
|
303 |
+
|
304 |
+
>>> ptr = JsonPointer('/~0/0/~1').path == '/~0/0/~1'
|
305 |
+
"""
|
306 |
+
parts = [escape(part) for part in self.parts]
|
307 |
+
return ''.join('/' + part for part in parts)
|
308 |
+
|
309 |
+
def __eq__(self, other):
|
310 |
+
"""Compares a pointer to another object
|
311 |
+
|
312 |
+
Pointers can be compared by comparing their strings (or splitted
|
313 |
+
strings), because no two different parts can point to the same
|
314 |
+
structure in an object (eg no different number representations)
|
315 |
+
"""
|
316 |
+
|
317 |
+
if not isinstance(other, JsonPointer):
|
318 |
+
return False
|
319 |
+
|
320 |
+
return self.parts == other.parts
|
321 |
+
|
322 |
+
def __hash__(self):
|
323 |
+
return hash(tuple(self.parts))
|
324 |
+
|
325 |
+
def __str__(self):
|
326 |
+
return self.path
|
327 |
+
|
328 |
+
def __repr__(self):
|
329 |
+
return type(self).__name__ + "(" + repr(self.path) + ")"
|
330 |
+
|
331 |
+
@classmethod
|
332 |
+
def from_parts(cls, parts):
|
333 |
+
"""Constructs a JsonPointer from a list of (unescaped) paths
|
334 |
+
|
335 |
+
>>> JsonPointer.from_parts(['a', '~', '/', 0]).path == '/a/~0/~1/0'
|
336 |
+
True
|
337 |
+
"""
|
338 |
+
parts = [escape(str(part)) for part in parts]
|
339 |
+
ptr = cls(''.join('/' + part for part in parts))
|
340 |
+
return ptr
|
341 |
+
|
342 |
+
|
343 |
+
def escape(s):
|
344 |
+
return s.replace('~', '~0').replace('/', '~1')
|
345 |
+
|
346 |
+
|
347 |
+
def unescape(s):
|
348 |
+
return s.replace('~1', '/').replace('~0', '~')
|
venv/Lib/site-packages/jupyter.py
ADDED
@@ -0,0 +1,7 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
"""Launch the root jupyter command"""
|
2 |
+
from __future__ import annotations
|
3 |
+
|
4 |
+
if __name__ == "__main__":
|
5 |
+
from jupyter_core.command import main
|
6 |
+
|
7 |
+
main()
|
venv/Lib/site-packages/nest_asyncio.py
ADDED
@@ -0,0 +1,219 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
"""Patch asyncio to allow nested event loops."""
|
2 |
+
|
3 |
+
import asyncio
|
4 |
+
import asyncio.events as events
|
5 |
+
import os
|
6 |
+
import sys
|
7 |
+
import threading
|
8 |
+
from contextlib import contextmanager, suppress
|
9 |
+
from heapq import heappop
|
10 |
+
|
11 |
+
|
12 |
+
def apply(loop=None):
|
13 |
+
"""Patch asyncio to make its event loop reentrant."""
|
14 |
+
_patch_asyncio()
|
15 |
+
_patch_policy()
|
16 |
+
_patch_tornado()
|
17 |
+
|
18 |
+
loop = loop or asyncio.get_event_loop()
|
19 |
+
_patch_loop(loop)
|
20 |
+
|
21 |
+
|
22 |
+
def _patch_asyncio():
|
23 |
+
"""Patch asyncio module to use pure Python tasks and futures."""
|
24 |
+
|
25 |
+
def run(main, *, debug=False):
|
26 |
+
loop = asyncio.get_event_loop()
|
27 |
+
loop.set_debug(debug)
|
28 |
+
task = asyncio.ensure_future(main)
|
29 |
+
try:
|
30 |
+
return loop.run_until_complete(task)
|
31 |
+
finally:
|
32 |
+
if not task.done():
|
33 |
+
task.cancel()
|
34 |
+
with suppress(asyncio.CancelledError):
|
35 |
+
loop.run_until_complete(task)
|
36 |
+
|
37 |
+
def _get_event_loop(stacklevel=3):
|
38 |
+
loop = events._get_running_loop()
|
39 |
+
if loop is None:
|
40 |
+
loop = events.get_event_loop_policy().get_event_loop()
|
41 |
+
return loop
|
42 |
+
|
43 |
+
# Use module level _current_tasks, all_tasks and patch run method.
|
44 |
+
if hasattr(asyncio, '_nest_patched'):
|
45 |
+
return
|
46 |
+
if sys.version_info >= (3, 6, 0):
|
47 |
+
asyncio.Task = asyncio.tasks._CTask = asyncio.tasks.Task = \
|
48 |
+
asyncio.tasks._PyTask
|
49 |
+
asyncio.Future = asyncio.futures._CFuture = asyncio.futures.Future = \
|
50 |
+
asyncio.futures._PyFuture
|
51 |
+
if sys.version_info < (3, 7, 0):
|
52 |
+
asyncio.tasks._current_tasks = asyncio.tasks.Task._current_tasks
|
53 |
+
asyncio.all_tasks = asyncio.tasks.Task.all_tasks
|
54 |
+
if sys.version_info >= (3, 9, 0):
|
55 |
+
events._get_event_loop = events.get_event_loop = \
|
56 |
+
asyncio.get_event_loop = _get_event_loop
|
57 |
+
asyncio.run = run
|
58 |
+
asyncio._nest_patched = True
|
59 |
+
|
60 |
+
|
61 |
+
def _patch_policy():
|
62 |
+
"""Patch the policy to always return a patched loop."""
|
63 |
+
|
64 |
+
def get_event_loop(self):
|
65 |
+
if self._local._loop is None:
|
66 |
+
loop = self.new_event_loop()
|
67 |
+
_patch_loop(loop)
|
68 |
+
self.set_event_loop(loop)
|
69 |
+
return self._local._loop
|
70 |
+
|
71 |
+
policy = events.get_event_loop_policy()
|
72 |
+
policy.__class__.get_event_loop = get_event_loop
|
73 |
+
|
74 |
+
|
75 |
+
def _patch_loop(loop):
|
76 |
+
"""Patch loop to make it reentrant."""
|
77 |
+
|
78 |
+
def run_forever(self):
|
79 |
+
with manage_run(self), manage_asyncgens(self):
|
80 |
+
while True:
|
81 |
+
self._run_once()
|
82 |
+
if self._stopping:
|
83 |
+
break
|
84 |
+
self._stopping = False
|
85 |
+
|
86 |
+
def run_until_complete(self, future):
|
87 |
+
with manage_run(self):
|
88 |
+
f = asyncio.ensure_future(future, loop=self)
|
89 |
+
if f is not future:
|
90 |
+
f._log_destroy_pending = False
|
91 |
+
while not f.done():
|
92 |
+
self._run_once()
|
93 |
+
if self._stopping:
|
94 |
+
break
|
95 |
+
if not f.done():
|
96 |
+
raise RuntimeError(
|
97 |
+
'Event loop stopped before Future completed.')
|
98 |
+
return f.result()
|
99 |
+
|
100 |
+
def _run_once(self):
|
101 |
+
"""
|
102 |
+
Simplified re-implementation of asyncio's _run_once that
|
103 |
+
runs handles as they become ready.
|
104 |
+
"""
|
105 |
+
ready = self._ready
|
106 |
+
scheduled = self._scheduled
|
107 |
+
while scheduled and scheduled[0]._cancelled:
|
108 |
+
heappop(scheduled)
|
109 |
+
|
110 |
+
timeout = (
|
111 |
+
0 if ready or self._stopping
|
112 |
+
else min(max(
|
113 |
+
scheduled[0]._when - self.time(), 0), 86400) if scheduled
|
114 |
+
else None)
|
115 |
+
event_list = self._selector.select(timeout)
|
116 |
+
self._process_events(event_list)
|
117 |
+
|
118 |
+
end_time = self.time() + self._clock_resolution
|
119 |
+
while scheduled and scheduled[0]._when < end_time:
|
120 |
+
handle = heappop(scheduled)
|
121 |
+
ready.append(handle)
|
122 |
+
|
123 |
+
for _ in range(len(ready)):
|
124 |
+
if not ready:
|
125 |
+
break
|
126 |
+
handle = ready.popleft()
|
127 |
+
if not handle._cancelled:
|
128 |
+
# preempt the current task so that that checks in
|
129 |
+
# Task.__step do not raise
|
130 |
+
curr_task = curr_tasks.pop(self, None)
|
131 |
+
|
132 |
+
try:
|
133 |
+
handle._run()
|
134 |
+
finally:
|
135 |
+
# restore the current task
|
136 |
+
if curr_task is not None:
|
137 |
+
curr_tasks[self] = curr_task
|
138 |
+
|
139 |
+
handle = None
|
140 |
+
|
141 |
+
@contextmanager
|
142 |
+
def manage_run(self):
|
143 |
+
"""Set up the loop for running."""
|
144 |
+
self._check_closed()
|
145 |
+
old_thread_id = self._thread_id
|
146 |
+
old_running_loop = events._get_running_loop()
|
147 |
+
try:
|
148 |
+
self._thread_id = threading.get_ident()
|
149 |
+
events._set_running_loop(self)
|
150 |
+
self._num_runs_pending += 1
|
151 |
+
if self._is_proactorloop:
|
152 |
+
if self._self_reading_future is None:
|
153 |
+
self.call_soon(self._loop_self_reading)
|
154 |
+
yield
|
155 |
+
finally:
|
156 |
+
self._thread_id = old_thread_id
|
157 |
+
events._set_running_loop(old_running_loop)
|
158 |
+
self._num_runs_pending -= 1
|
159 |
+
if self._is_proactorloop:
|
160 |
+
if (self._num_runs_pending == 0
|
161 |
+
and self._self_reading_future is not None):
|
162 |
+
ov = self._self_reading_future._ov
|
163 |
+
self._self_reading_future.cancel()
|
164 |
+
if ov is not None:
|
165 |
+
self._proactor._unregister(ov)
|
166 |
+
self._self_reading_future = None
|
167 |
+
|
168 |
+
@contextmanager
|
169 |
+
def manage_asyncgens(self):
|
170 |
+
if not hasattr(sys, 'get_asyncgen_hooks'):
|
171 |
+
# Python version is too old.
|
172 |
+
return
|
173 |
+
old_agen_hooks = sys.get_asyncgen_hooks()
|
174 |
+
try:
|
175 |
+
self._set_coroutine_origin_tracking(self._debug)
|
176 |
+
if self._asyncgens is not None:
|
177 |
+
sys.set_asyncgen_hooks(
|
178 |
+
firstiter=self._asyncgen_firstiter_hook,
|
179 |
+
finalizer=self._asyncgen_finalizer_hook)
|
180 |
+
yield
|
181 |
+
finally:
|
182 |
+
self._set_coroutine_origin_tracking(False)
|
183 |
+
if self._asyncgens is not None:
|
184 |
+
sys.set_asyncgen_hooks(*old_agen_hooks)
|
185 |
+
|
186 |
+
def _check_running(self):
|
187 |
+
"""Do not throw exception if loop is already running."""
|
188 |
+
pass
|
189 |
+
|
190 |
+
if hasattr(loop, '_nest_patched'):
|
191 |
+
return
|
192 |
+
if not isinstance(loop, asyncio.BaseEventLoop):
|
193 |
+
raise ValueError('Can\'t patch loop of type %s' % type(loop))
|
194 |
+
cls = loop.__class__
|
195 |
+
cls.run_forever = run_forever
|
196 |
+
cls.run_until_complete = run_until_complete
|
197 |
+
cls._run_once = _run_once
|
198 |
+
cls._check_running = _check_running
|
199 |
+
cls._check_runnung = _check_running # typo in Python 3.7 source
|
200 |
+
cls._num_runs_pending = 1 if loop.is_running() else 0
|
201 |
+
cls._is_proactorloop = (
|
202 |
+
os.name == 'nt' and issubclass(cls, asyncio.ProactorEventLoop))
|
203 |
+
if sys.version_info < (3, 7, 0):
|
204 |
+
cls._set_coroutine_origin_tracking = cls._set_coroutine_wrapper
|
205 |
+
curr_tasks = asyncio.tasks._current_tasks \
|
206 |
+
if sys.version_info >= (3, 7, 0) else asyncio.Task._current_tasks
|
207 |
+
cls._nest_patched = True
|
208 |
+
|
209 |
+
|
210 |
+
def _patch_tornado():
|
211 |
+
"""
|
212 |
+
If tornado is imported before nest_asyncio, make tornado aware of
|
213 |
+
the pure-Python asyncio Future.
|
214 |
+
"""
|
215 |
+
if 'tornado' in sys.modules:
|
216 |
+
import tornado.concurrent as tc # type: ignore
|
217 |
+
tc.Future = asyncio.Future
|
218 |
+
if asyncio.Future not in tc.FUTURES:
|
219 |
+
tc.FUTURES += (asyncio.Future,)
|
venv/Lib/site-packages/numpy-2.2.5-cp312-cp312-win_amd64.whl
ADDED
File without changes
|
venv/Lib/site-packages/pandocfilters.py
ADDED
@@ -0,0 +1,304 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
# Author: John MacFarlane <[email protected]>
|
2 |
+
# Copyright: (C) 2013 John MacFarlane
|
3 |
+
# License: BSD3
|
4 |
+
|
5 |
+
"""
|
6 |
+
Functions to aid writing python scripts that process the pandoc
|
7 |
+
AST serialized as JSON.
|
8 |
+
"""
|
9 |
+
|
10 |
+
import codecs
|
11 |
+
import hashlib
|
12 |
+
import io
|
13 |
+
import json
|
14 |
+
import os
|
15 |
+
import sys
|
16 |
+
import atexit
|
17 |
+
import shutil
|
18 |
+
import tempfile
|
19 |
+
|
20 |
+
|
21 |
+
# some utility-functions: make it easier to create your own filters
|
22 |
+
|
23 |
+
|
24 |
+
def get_filename4code(module, content, ext=None):
|
25 |
+
"""Generate filename based on content
|
26 |
+
|
27 |
+
The function ensures that the (temporary) directory exists, so that the
|
28 |
+
file can be written.
|
29 |
+
|
30 |
+
By default, the directory won't be cleaned up,
|
31 |
+
so a filter can use the directory as a cache and
|
32 |
+
decide not to regenerate if there's no change.
|
33 |
+
|
34 |
+
In case the user preferres the files to be temporary files,
|
35 |
+
an environment variable `PANDOCFILTER_CLEANUP` can be set to
|
36 |
+
any non-empty value such as `1` to
|
37 |
+
make sure the directory is created in a temporary location and removed
|
38 |
+
after finishing the filter. In this case there's no caching and files
|
39 |
+
will be regenerated each time the filter is run.
|
40 |
+
|
41 |
+
Example:
|
42 |
+
filename = get_filename4code("myfilter", code)
|
43 |
+
"""
|
44 |
+
if os.getenv('PANDOCFILTER_CLEANUP'):
|
45 |
+
imagedir = tempfile.mkdtemp(prefix=module)
|
46 |
+
atexit.register(lambda: shutil.rmtree(imagedir))
|
47 |
+
else:
|
48 |
+
imagedir = module + "-images"
|
49 |
+
fn = hashlib.sha1(content.encode(sys.getfilesystemencoding())).hexdigest()
|
50 |
+
try:
|
51 |
+
os.makedirs(imagedir, exist_ok=True)
|
52 |
+
sys.stderr.write('Created directory ' + imagedir + '\n')
|
53 |
+
except OSError:
|
54 |
+
sys.stderr.write('Could not create directory "' + imagedir + '"\n')
|
55 |
+
if ext:
|
56 |
+
fn += "." + ext
|
57 |
+
return os.path.join(imagedir, fn)
|
58 |
+
|
59 |
+
def get_value(kv, key, value = None):
|
60 |
+
"""get value from the keyvalues (options)"""
|
61 |
+
res = []
|
62 |
+
for k, v in kv:
|
63 |
+
if k == key:
|
64 |
+
value = v
|
65 |
+
else:
|
66 |
+
res.append([k, v])
|
67 |
+
return value, res
|
68 |
+
|
69 |
+
def get_caption(kv):
|
70 |
+
"""get caption from the keyvalues (options)
|
71 |
+
|
72 |
+
Example:
|
73 |
+
if key == 'CodeBlock':
|
74 |
+
[[ident, classes, keyvals], code] = value
|
75 |
+
caption, typef, keyvals = get_caption(keyvals)
|
76 |
+
...
|
77 |
+
return Para([Image([ident, [], keyvals], caption, [filename, typef])])
|
78 |
+
"""
|
79 |
+
caption = []
|
80 |
+
typef = ""
|
81 |
+
value, res = get_value(kv, u"caption")
|
82 |
+
if value is not None:
|
83 |
+
caption = [Str(value)]
|
84 |
+
typef = "fig:"
|
85 |
+
|
86 |
+
return caption, typef, res
|
87 |
+
|
88 |
+
|
89 |
+
def get_extension(format, default, **alternates):
|
90 |
+
"""get the extension for the result, needs a default and some specialisations
|
91 |
+
|
92 |
+
Example:
|
93 |
+
filetype = get_extension(format, "png", html="svg", latex="eps")
|
94 |
+
"""
|
95 |
+
try:
|
96 |
+
return alternates[format]
|
97 |
+
except KeyError:
|
98 |
+
return default
|
99 |
+
|
100 |
+
# end of utilities
|
101 |
+
|
102 |
+
|
103 |
+
def walk(x, action, format, meta):
|
104 |
+
"""Walk a tree, applying an action to every object.
|
105 |
+
Returns a modified tree. An action is a function of the form
|
106 |
+
`action(key, value, format, meta)`, where:
|
107 |
+
|
108 |
+
* `key` is the type of the pandoc object (e.g. 'Str', 'Para') `value` is
|
109 |
+
* the contents of the object (e.g. a string for 'Str', a list of
|
110 |
+
inline elements for 'Para')
|
111 |
+
* `format` is the target output format (as supplied by the
|
112 |
+
`format` argument of `walk`)
|
113 |
+
* `meta` is the document's metadata
|
114 |
+
|
115 |
+
The return of an action is either:
|
116 |
+
|
117 |
+
* `None`: this means that the object should remain unchanged
|
118 |
+
* a pandoc object: this will replace the original object
|
119 |
+
* a list of pandoc objects: these will replace the original object; the
|
120 |
+
list is merged with the neighbors of the orignal objects (spliced into
|
121 |
+
the list the original object belongs to); returning an empty list deletes
|
122 |
+
the object
|
123 |
+
"""
|
124 |
+
if isinstance(x, list):
|
125 |
+
array = []
|
126 |
+
for item in x:
|
127 |
+
if isinstance(item, dict) and 't' in item:
|
128 |
+
res = action(item['t'],
|
129 |
+
item['c'] if 'c' in item else None, format, meta)
|
130 |
+
if res is None:
|
131 |
+
array.append(walk(item, action, format, meta))
|
132 |
+
elif isinstance(res, list):
|
133 |
+
for z in res:
|
134 |
+
array.append(walk(z, action, format, meta))
|
135 |
+
else:
|
136 |
+
array.append(walk(res, action, format, meta))
|
137 |
+
else:
|
138 |
+
array.append(walk(item, action, format, meta))
|
139 |
+
return array
|
140 |
+
elif isinstance(x, dict):
|
141 |
+
return {k: walk(v, action, format, meta) for k, v in x.items()}
|
142 |
+
else:
|
143 |
+
return x
|
144 |
+
|
145 |
+
def toJSONFilter(action):
|
146 |
+
"""Like `toJSONFilters`, but takes a single action as argument.
|
147 |
+
"""
|
148 |
+
toJSONFilters([action])
|
149 |
+
|
150 |
+
|
151 |
+
def toJSONFilters(actions):
|
152 |
+
"""Generate a JSON-to-JSON filter from stdin to stdout
|
153 |
+
|
154 |
+
The filter:
|
155 |
+
|
156 |
+
* reads a JSON-formatted pandoc document from stdin
|
157 |
+
* transforms it by walking the tree and performing the actions
|
158 |
+
* returns a new JSON-formatted pandoc document to stdout
|
159 |
+
|
160 |
+
The argument `actions` is a list of functions of the form
|
161 |
+
`action(key, value, format, meta)`, as described in more
|
162 |
+
detail under `walk`.
|
163 |
+
|
164 |
+
This function calls `applyJSONFilters`, with the `format`
|
165 |
+
argument provided by the first command-line argument,
|
166 |
+
if present. (Pandoc sets this by default when calling
|
167 |
+
filters.)
|
168 |
+
"""
|
169 |
+
try:
|
170 |
+
input_stream = io.TextIOWrapper(sys.stdin.buffer, encoding='utf-8')
|
171 |
+
except AttributeError:
|
172 |
+
# Python 2 does not have sys.stdin.buffer.
|
173 |
+
# REF: https://stackoverflow.com/questions/2467928/python-unicodeencode
|
174 |
+
input_stream = codecs.getreader("utf-8")(sys.stdin)
|
175 |
+
|
176 |
+
source = input_stream.read()
|
177 |
+
if len(sys.argv) > 1:
|
178 |
+
format = sys.argv[1]
|
179 |
+
else:
|
180 |
+
format = ""
|
181 |
+
|
182 |
+
sys.stdout.write(applyJSONFilters(actions, source, format))
|
183 |
+
|
184 |
+
def applyJSONFilters(actions, source, format=""):
|
185 |
+
"""Walk through JSON structure and apply filters
|
186 |
+
|
187 |
+
This:
|
188 |
+
|
189 |
+
* reads a JSON-formatted pandoc document from a source string
|
190 |
+
* transforms it by walking the tree and performing the actions
|
191 |
+
* returns a new JSON-formatted pandoc document as a string
|
192 |
+
|
193 |
+
The `actions` argument is a list of functions (see `walk`
|
194 |
+
for a full description).
|
195 |
+
|
196 |
+
The argument `source` is a string encoded JSON object.
|
197 |
+
|
198 |
+
The argument `format` is a string describing the output format.
|
199 |
+
|
200 |
+
Returns a the new JSON-formatted pandoc document.
|
201 |
+
"""
|
202 |
+
|
203 |
+
doc = json.loads(source)
|
204 |
+
|
205 |
+
if 'meta' in doc:
|
206 |
+
meta = doc['meta']
|
207 |
+
elif doc[0]: # old API
|
208 |
+
meta = doc[0]['unMeta']
|
209 |
+
else:
|
210 |
+
meta = {}
|
211 |
+
altered = doc
|
212 |
+
for action in actions:
|
213 |
+
altered = walk(altered, action, format, meta)
|
214 |
+
|
215 |
+
return json.dumps(altered)
|
216 |
+
|
217 |
+
|
218 |
+
def stringify(x):
|
219 |
+
"""Walks the tree x and returns concatenated string content,
|
220 |
+
leaving out all formatting.
|
221 |
+
"""
|
222 |
+
result = []
|
223 |
+
|
224 |
+
def go(key, val, format, meta):
|
225 |
+
if key in ['Str', 'MetaString']:
|
226 |
+
result.append(val)
|
227 |
+
elif key == 'Code':
|
228 |
+
result.append(val[1])
|
229 |
+
elif key == 'Math':
|
230 |
+
result.append(val[1])
|
231 |
+
elif key == 'LineBreak':
|
232 |
+
result.append(" ")
|
233 |
+
elif key == 'SoftBreak':
|
234 |
+
result.append(" ")
|
235 |
+
elif key == 'Space':
|
236 |
+
result.append(" ")
|
237 |
+
|
238 |
+
walk(x, go, "", {})
|
239 |
+
return ''.join(result)
|
240 |
+
|
241 |
+
|
242 |
+
def attributes(attrs):
|
243 |
+
"""Returns an attribute list, constructed from the
|
244 |
+
dictionary attrs.
|
245 |
+
"""
|
246 |
+
attrs = attrs or {}
|
247 |
+
ident = attrs.get("id", "")
|
248 |
+
classes = attrs.get("classes", [])
|
249 |
+
keyvals = [[x, attrs[x]] for x in attrs if (x != "classes" and x != "id")]
|
250 |
+
return [ident, classes, keyvals]
|
251 |
+
|
252 |
+
|
253 |
+
def elt(eltType, numargs):
|
254 |
+
def fun(*args):
|
255 |
+
lenargs = len(args)
|
256 |
+
if lenargs != numargs:
|
257 |
+
raise ValueError(eltType + ' expects ' + str(numargs) +
|
258 |
+
' arguments, but given ' + str(lenargs))
|
259 |
+
if numargs == 0:
|
260 |
+
xs = []
|
261 |
+
elif len(args) == 1:
|
262 |
+
xs = args[0]
|
263 |
+
else:
|
264 |
+
xs = list(args)
|
265 |
+
return {'t': eltType, 'c': xs}
|
266 |
+
return fun
|
267 |
+
|
268 |
+
# Constructors for block elements
|
269 |
+
|
270 |
+
Plain = elt('Plain', 1)
|
271 |
+
Para = elt('Para', 1)
|
272 |
+
CodeBlock = elt('CodeBlock', 2)
|
273 |
+
RawBlock = elt('RawBlock', 2)
|
274 |
+
BlockQuote = elt('BlockQuote', 1)
|
275 |
+
OrderedList = elt('OrderedList', 2)
|
276 |
+
BulletList = elt('BulletList', 1)
|
277 |
+
DefinitionList = elt('DefinitionList', 1)
|
278 |
+
Header = elt('Header', 3)
|
279 |
+
HorizontalRule = elt('HorizontalRule', 0)
|
280 |
+
Table = elt('Table', 5)
|
281 |
+
Div = elt('Div', 2)
|
282 |
+
Null = elt('Null', 0)
|
283 |
+
|
284 |
+
# Constructors for inline elements
|
285 |
+
|
286 |
+
Str = elt('Str', 1)
|
287 |
+
Emph = elt('Emph', 1)
|
288 |
+
Strong = elt('Strong', 1)
|
289 |
+
Strikeout = elt('Strikeout', 1)
|
290 |
+
Superscript = elt('Superscript', 1)
|
291 |
+
Subscript = elt('Subscript', 1)
|
292 |
+
SmallCaps = elt('SmallCaps', 1)
|
293 |
+
Quoted = elt('Quoted', 2)
|
294 |
+
Cite = elt('Cite', 2)
|
295 |
+
Code = elt('Code', 2)
|
296 |
+
Space = elt('Space', 0)
|
297 |
+
LineBreak = elt('LineBreak', 0)
|
298 |
+
Math = elt('Math', 2)
|
299 |
+
RawInline = elt('RawInline', 2)
|
300 |
+
Link = elt('Link', 3)
|
301 |
+
Image = elt('Image', 3)
|
302 |
+
Note = elt('Note', 1)
|
303 |
+
SoftBreak = elt('SoftBreak', 0)
|
304 |
+
Span = elt('Span', 2)
|
venv/Lib/site-packages/pylab.py
ADDED
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
1 |
+
from matplotlib.pylab import * # noqa: F401, F403
|
2 |
+
import matplotlib.pylab
|
3 |
+
__doc__ = matplotlib.pylab.__doc__
|
venv/Lib/site-packages/pythoncom.py
ADDED
@@ -0,0 +1,4 @@
|
|
|
|
|
|
|
|
|
|
|
1 |
+
# Magic utility that "redirects" to pythoncomXX.dll
|
2 |
+
import pywintypes
|
3 |
+
|
4 |
+
pywintypes.__import_pywin32_system_module__("pythoncom", globals())
|
venv/Lib/site-packages/pywin32.version.txt
ADDED
@@ -0,0 +1 @@
|
|
|
|
|
1 |
+
310
|
venv/Lib/site-packages/rfc3339_validator.py
ADDED
@@ -0,0 +1,51 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
# -*- coding: utf-8 -*-
|
2 |
+
|
3 |
+
__author__ = """Nicolas Aimetti"""
|
4 |
+
__email__ = '[email protected]'
|
5 |
+
__version__ = '0.1.4'
|
6 |
+
|
7 |
+
import re
|
8 |
+
import calendar
|
9 |
+
import six
|
10 |
+
|
11 |
+
RFC3339_REGEX_FLAGS = 0
|
12 |
+
if six.PY3:
|
13 |
+
RFC3339_REGEX_FLAGS |= re.ASCII
|
14 |
+
|
15 |
+
RFC3339_REGEX = re.compile(r"""
|
16 |
+
^
|
17 |
+
(\d{4}) # Year
|
18 |
+
-
|
19 |
+
(0[1-9]|1[0-2]) # Month
|
20 |
+
-
|
21 |
+
(\d{2}) # Day
|
22 |
+
T
|
23 |
+
(?:[01]\d|2[0123]) # Hours
|
24 |
+
:
|
25 |
+
(?:[0-5]\d) # Minutes
|
26 |
+
:
|
27 |
+
(?:[0-5]\d) # Seconds
|
28 |
+
(?:\.\d+)? # Secfrac
|
29 |
+
(?: Z # UTC
|
30 |
+
| [+-](?:[01]\d|2[0123]):[0-5]\d # Offset
|
31 |
+
)
|
32 |
+
$
|
33 |
+
""", re.VERBOSE | RFC3339_REGEX_FLAGS)
|
34 |
+
|
35 |
+
|
36 |
+
def validate_rfc3339(date_string):
|
37 |
+
"""
|
38 |
+
Validates dates against RFC3339 datetime format
|
39 |
+
Leap seconds are no supported.
|
40 |
+
"""
|
41 |
+
m = RFC3339_REGEX.match(date_string)
|
42 |
+
if m is None:
|
43 |
+
return False
|
44 |
+
year, month, day = map(int, m.groups())
|
45 |
+
if not year:
|
46 |
+
# Year 0 is not valid a valid date
|
47 |
+
return False
|
48 |
+
(_, max_day) = calendar.monthrange(year, month)
|
49 |
+
if not 1 <= day <= max_day:
|
50 |
+
return False
|
51 |
+
return True
|
venv/Lib/site-packages/rfc3986_validator.py
ADDED
@@ -0,0 +1,106 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
import re
|
2 |
+
|
3 |
+
__version__ = '0.1.1'
|
4 |
+
__author__ = 'Nicolas Aimetti <[email protected]>'
|
5 |
+
__all__ = ['validate_rfc3986']
|
6 |
+
|
7 |
+
# Following regex rules references the ABNF terminology from
|
8 |
+
# [RFC3986](https://tools.ietf.org/html/rfc3986#appendix-A)
|
9 |
+
|
10 |
+
|
11 |
+
# IPv6 validation rule
|
12 |
+
IPv6_RE = (
|
13 |
+
r"(?:(?:[0-9A-Fa-f]{1,4}:){6}(?:[0-9A-Fa-f]{1,4}:[0-9A-Fa-f]{1,4}|(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9]["
|
14 |
+
r"0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?))|::(?:[0-9A-Fa-f]{1,4}:){5}(?:[0-9A-Fa-f]{1,"
|
15 |
+
r"4}:[0-9A-Fa-f]{1,4}|(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9]["
|
16 |
+
r"0-9]?))|(?:[0-9A-Fa-f]{1,4})?::(?:[0-9A-Fa-f]{1,4}:){4}(?:[0-9A-Fa-f]{1,4}:[0-9A-Fa-f]{1,4}|(?:(?:25[0-5]|2["
|
17 |
+
r"0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?))|(?:(?:[0-9A-Fa-f]{1,"
|
18 |
+
r"4}:)?[0-9A-Fa-f]{1,4})?::(?:[0-9A-Fa-f]{1,4}:){3}(?:[0-9A-Fa-f]{1,4}:[0-9A-Fa-f]{1,4}|(?:(?:25[0-5]|2[0-4]["
|
19 |
+
r"0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?))|(?:(?:[0-9A-Fa-f]{1,4}:){,"
|
20 |
+
r"2}[0-9A-Fa-f]{1,4})?::(?:[0-9A-Fa-f]{1,4}:){2}(?:[0-9A-Fa-f]{1,4}:[0-9A-Fa-f]{1,4}|(?:(?:25[0-5]|2[0-4]["
|
21 |
+
r"0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?))|(?:(?:[0-9A-Fa-f]{1,4}:){,"
|
22 |
+
r"3}[0-9A-Fa-f]{1,4})?::(?:[0-9A-Fa-f]{1,4}:)(?:[0-9A-Fa-f]{1,4}:[0-9A-Fa-f]{1,4}|(?:(?:25[0-5]|2[0-4][0-9]|["
|
23 |
+
r"01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?))|(?:(?:[0-9A-Fa-f]{1,4}:){,4}[0-9A-Fa-f]{1,"
|
24 |
+
r"4})?::(?:[0-9A-Fa-f]{1,4}:[0-9A-Fa-f]{1,4}|(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2["
|
25 |
+
r"0-4][0-9]|[01]?[0-9][0-9]?))|(?:(?:[0-9A-Fa-f]{1,4}:){,5}[0-9A-Fa-f]{1,4})?::[0-9A-Fa-f]{1,4}|(?:(?:["
|
26 |
+
r"0-9A-Fa-f]{1,4}:){,6}[0-9A-Fa-f]{1,4})?::)"
|
27 |
+
)
|
28 |
+
|
29 |
+
|
30 |
+
# An authority is defined as: [ userinfo "@" ] host [ ":" port ]
|
31 |
+
# \[(?:{ip_v6} | v[0-9A-Fa-f]+\.[a-zA-Z0-9_.~\-!$ & '()*+,;=:]+)\] # IP-literal
|
32 |
+
AUTHORITY_RE = r"""
|
33 |
+
(?:(?:[a-zA-Z0-9_.~\-!$&'()*+,;=:]|%[0-9A-Fa-f]{{2}})*@)? # user info
|
34 |
+
(?:
|
35 |
+
\[(?:{ip_v6}|v[0-9A-Fa-f]+\.[a-zA-Z0-9_.~\-!$&'()*+,;=:]+)\] # IP-literal
|
36 |
+
| (?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){{3}}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?) # IPv4
|
37 |
+
| (?:[a-zA-Z0-9_.~\-!$&'()*+,;=]|%[0-9A-Fa-f]{{2}})* # reg-name
|
38 |
+
) # host
|
39 |
+
(?::[0-9]*)? # port
|
40 |
+
""".format(ip_v6=IPv6_RE,)
|
41 |
+
# Path char regex rule
|
42 |
+
PCHAR_RE = r"(?:[a-zA-Z0-9_.~\-!$&'()*+,;=:@]|%[0-9A-Fa-f]{2})"
|
43 |
+
# Query and Fragment rules are exactly the same
|
44 |
+
QUERY_RE = r"(?:[a-zA-Z0-9_.~\-!$&'()*+,;=:@/?]|%[0-9A-Fa-f]{2})*"
|
45 |
+
# An URI is defined as: scheme ":" hier-part [ "?" query ] [ "#" fragment ]
|
46 |
+
URI_RE = r"""
|
47 |
+
[a-zA-Z][a-zA-Z0-9+.-]* #scheme
|
48 |
+
:
|
49 |
+
(?:
|
50 |
+
//
|
51 |
+
{authority}
|
52 |
+
(?:/{pchar}*)* # path-abempty
|
53 |
+
| /(?:{pchar}+ (?:/{pchar}*)*)? # path-absolute
|
54 |
+
| {pchar}+ (?:/{pchar}*)* # path-rootless
|
55 |
+
| # or nothing
|
56 |
+
) # hier-part
|
57 |
+
(?:\?{query})? # Query
|
58 |
+
(?:\#{fragment})? # Fragment
|
59 |
+
""".format(
|
60 |
+
authority=AUTHORITY_RE,
|
61 |
+
query=QUERY_RE,
|
62 |
+
fragment=QUERY_RE,
|
63 |
+
pchar=PCHAR_RE
|
64 |
+
)
|
65 |
+
|
66 |
+
# A relative-ref is defined as: relative-part [ "?" query ] [ "#" fragment ]
|
67 |
+
RELATIVE_REF_RE = r"""
|
68 |
+
(?:
|
69 |
+
//
|
70 |
+
{authority}
|
71 |
+
(?:/{pchar}*)* # path-abempty
|
72 |
+
| /(?:{pchar}+ (?:/{pchar}*)*)? # path-absolute
|
73 |
+
| (?:[a-zA-Z0-9_.~\-!$&'()*+,;=@]|%[0-9A-Fa-f]{{2}})+ (?:/{pchar}*)* # path-noscheme
|
74 |
+
| # or nothing
|
75 |
+
) # relative-part
|
76 |
+
(?:\?{query})? # Query
|
77 |
+
(?:\#{fragment})? # Fragment
|
78 |
+
""".format(
|
79 |
+
authority=AUTHORITY_RE,
|
80 |
+
query=QUERY_RE,
|
81 |
+
fragment=QUERY_RE,
|
82 |
+
pchar=PCHAR_RE
|
83 |
+
)
|
84 |
+
# Compiled URI regex rule
|
85 |
+
URI_RE_COMP = re.compile(r"^{uri_re}$".format(uri_re=URI_RE), re.VERBOSE)
|
86 |
+
# Compiled URI-reference regex rule. URI-reference is defined as: URI / relative-ref
|
87 |
+
URI_REF_RE_COMP = re.compile(r"^(?:{uri_re}|{relative_ref})$".format(
|
88 |
+
uri_re=URI_RE,
|
89 |
+
relative_ref=RELATIVE_REF_RE,
|
90 |
+
), re.VERBOSE)
|
91 |
+
|
92 |
+
|
93 |
+
def validate_rfc3986(url, rule='URI'):
|
94 |
+
"""
|
95 |
+
Validates strings according to RFC3986
|
96 |
+
|
97 |
+
:param url: String cointaining URI to validate
|
98 |
+
:param rule: It could be 'URI' (default) or 'URI_reference'.
|
99 |
+
:return: True or False
|
100 |
+
"""
|
101 |
+
if rule == 'URI':
|
102 |
+
return URI_RE_COMP.match(url)
|
103 |
+
elif rule == 'URI_reference':
|
104 |
+
return URI_REF_RE_COMP.match(url)
|
105 |
+
else:
|
106 |
+
raise ValueError('Invalid rule')
|
venv/etc/jupyter/jupyter_server_config.d/jupyter_server_terminals.json
ADDED
@@ -0,0 +1,7 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
{
|
2 |
+
"ServerApp": {
|
3 |
+
"jpserver_extensions": {
|
4 |
+
"jupyter_server_terminals": true
|
5 |
+
}
|
6 |
+
}
|
7 |
+
}
|
venv/etc/jupyter/jupyter_server_config.d/jupyterlab.json
ADDED
@@ -0,0 +1,7 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
{
|
2 |
+
"ServerApp": {
|
3 |
+
"jpserver_extensions": {
|
4 |
+
"jupyterlab": true
|
5 |
+
}
|
6 |
+
}
|
7 |
+
}
|
venv/etc/jupyter/jupyter_server_config.d/notebook.json
ADDED
@@ -0,0 +1,7 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
{
|
2 |
+
"ServerApp": {
|
3 |
+
"jpserver_extensions": {
|
4 |
+
"notebook": true
|
5 |
+
}
|
6 |
+
}
|
7 |
+
}
|
venv/etc/jupyter/jupyter_server_config.d/notebook_shim.json
ADDED
@@ -0,0 +1,7 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
{
|
2 |
+
"ServerApp": {
|
3 |
+
"jpserver_extensions": {
|
4 |
+
"notebook_shim": true
|
5 |
+
}
|
6 |
+
}
|
7 |
+
}
|
venv/etc/jupyter/labconfig/page_config.json
ADDED
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
1 |
+
{
|
2 |
+
"lockedExtensions": {}
|
3 |
+
}
|
venv/etc/jupyter/nbconfig/notebook.d/widgetsnbextension.json
ADDED
@@ -0,0 +1,5 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
{
|
2 |
+
"load_extensions": {
|
3 |
+
"jupyter-js-widgets/extension": true
|
4 |
+
}
|
5 |
+
}
|