def _test_patch(code): return patch_name(ast.parse(code).body[0])
s = "@patch\ndef _f(self:_T): ..."
test_eq('_T._f', _test_patch(s))doclinks
Create the module index
patch_name
def patch_name(
o
):
If o is decorated with patch or patch_to, return its class-prefix name
s = "@patch_to(_T)\ndef _g(self): ..."
test_eq('_T._g', _test_patch(s))# Get all patched classes when patching with a union
s = "@patch\ndef _f(self:_T|_U|_V): ..."
test_eq(_test_patch(s), ['_T._f', '_U._f', '_V._f'])# _build_modidx()Export a notebook
nbglob
def nbglob(
path:NoneType=None, # path to start searching
skip_folder_re:str='^[_.]', # Skip folders matching regex,
file_glob:str='*.ipynb', # Only include files matching glob
skip_file_re:str='^[_.]', # Skip files matching regex
key:str='nbs_path', as_path:bool=False, recursive:bool=True, # search subfolders
symlinks:bool=True, # follow symlinks?
file_re:str=None, # Only include files matching regex
folder_re:str=None, # Only enter folders matching regex
skip_file_glob:str=None, # Skip files matching glob
func:callable=<function join at 0x7f549ed72e60>, # function to apply to each matched file
ret_folders:bool=False, # return folders, not just files
sort:bool=True, # sort files by name within each folder
types:str \| list=None, # list or comma-separated str of ext types from: py, js, java, c, cpp, rb, r, ex, sh, web, doc, cfg
exts:str \| list=None, # list or comma-separated str of exts to include
): # Paths to matched files
Find all files in a directory matching an extension given a config key.
nbglob_cli
def nbglob_cli(
path:str=None, # Path to notebooks
symlinks:bool=False, # Follow symlinks?
file_glob:str='*.ipynb', # Only include files matching glob
file_re:str=None, # Only include files matching regex
folder_re:str=None, # Only enter folders matching regex
skip_file_glob:str=None, # Skip files matching glob
skip_file_re:str='^[_.]', # Skip files matching regex
skip_folder_re:str='^[_.]', # Skip folders matching regex
):
Find all files in a directory matching an extension given a config key.
nbdev_export
def nbdev_export(
path:str=None, # Path or filename
procs:<tokens naming the export processors to use.>='black_format', symlinks:bool=False, # Follow symlinks?
file_glob:str='*.ipynb', # Only include files matching glob
file_re:str=None, # Only include files matching regex
folder_re:str=None, # Only enter folders matching regex
skip_file_glob:str=None, # Skip files matching glob
skip_file_re:str='^[_.]', # Skip files matching regex
skip_folder_re:str='^[_.]', # Skip folders matching regex
):
Export notebooks in path to Python modules
procs names the optional processors you wish to run on the exported cells of your notebook.
N.B.: the black_format processor is passed in by default. But it is a no-op, unless black_formatting=True is set in your settings.ini configuration. You can omit it from nbdev_export on the command line by passing in --procs.
Construct Index
create_index
def create_index(
url, pre:NoneType=None
):
Create a documentation index from a sphinx inventory file at url, with optional prefix pre
url = 'https://docs.python.org/3'
syms = create_index(url)
for b in syms['builtins']:
b = b.split('.')
if len(b) != 2: continue
b = b[1]
assert b in bset
dict(list(syms['builtins'].items())[:10]){'builtins.bool': 'https://docs.python.org/3/library/functions.html#bool',
'builtins.bytearray': 'https://docs.python.org/3/library/stdtypes.html#bytearray',
'builtins.bytes': 'https://docs.python.org/3/library/stdtypes.html#bytes',
'builtins.complex': 'https://docs.python.org/3/library/functions.html#complex',
'builtins.dict': 'https://docs.python.org/3/library/stdtypes.html#dict',
'builtins.float': 'https://docs.python.org/3/library/functions.html#float',
'builtins.frozenset': 'https://docs.python.org/3/library/stdtypes.html#frozenset',
'builtins.int': 'https://docs.python.org/3/library/functions.html#int',
'builtins.list': 'https://docs.python.org/3/library/stdtypes.html#list',
'builtins.memoryview': 'https://docs.python.org/3/library/stdtypes.html#memoryview'}
Query the module index
NbdevLookup
def NbdevLookup(
strip_libs:NoneType=None, incl_libs:NoneType=None, skip_mods:NoneType=None, ns:NoneType=None
):
Mapping from symbol names to docs and source URLs
Indexing returns a link to the symbol’s docs, along with the name of the source file the source URL if available.
c = NbdevLookup()
c['nbdev.doclinks.NbdevLookup']('https://nbdev.fast.ai/api/doclinks.html#nbdevlookup',
'nbdev/doclinks.py',
'https://github.com/AnswerDotAI/nbdev/blob/main/nbdev/doclinks.py')
NbdevLookup.doc
def doc(
sym
):
Link to docs for sym
c.doc('nbdev.doclinks.NbdevLookup')'https://nbdev.fast.ai/api/doclinks.html#nbdevlookup'
Symbol names are taken from libraries registered using the ‘nbdev’ entry point. By default, all libraries with this entry point are searched, but full symbol names (including module prefix) are required.
assert c.doc('numpy.array').startswith('http')
assert not c.doc('numpy.Array')
assert c.doc('NbdevLookup').endswith('#nbdevlookup')
assert not c.doc('array')Pass strip_libs to list libraries which should be available without requiring a module prefix.
c = NbdevLookup(strip_libs=('nbdev', 'nbdev_numpy'))
assert c.doc('array').startswith('http')NbdevLookup.code
def code(
sym
):
Link to source code for sym
NbdevLookup().code('fastcore.net.urlsend')'https://github.com/AnswerDotAI/fastcore/blob/main/fastcore/net.py#LNone'
NbdevLookup.linkify
def linkify(
md
):
md = """This is a link to `numpy.array` and to `array()` and to `get_config()` but not a link to `foobar`.
And not a link to <code>dict2nb</code>.
This is not a link to `get_config`
```
This isn't a link to `get_config` either
```"""print(NbdevLookup(('nbdev','numpy')).linkify(md))This is a link to [`numpy.array`](https://numpy.org/doc/stable/reference/generated/numpy.array.html#numpy.array) and to `array()` and to [`get_config()`](https://nbdev.fast.ai/api/config.html#get_config) but not a link to `foobar`.
And not a link to <code>dict2nb</code>.
This is not a link to `get_config`
```
This isn't a link to `get_config` either
```
# Test code blocks
md = """```python
def foo():
return `bar`
```"""
assert NbdevLookup().linkify(md) == md# Test builtins
md = "`builtins.str.split`"
NbdevLookup().linkify(md)'[`builtins.str.split`](https://docs.python.org/3/library/stdtypes.html#str.split)'
# ... now with stripping
md = "`str.split` and `str`"
NbdevLookup('nbdev_stdlib').linkify(md)'[`str.split`](https://docs.python.org/3/library/stdtypes.html#str.split) and [`str`](https://docs.python.org/3/library/stdtypes.html#str)'
When there is a conflict, the linkification will apply in the order of the stripped libraries and then by alphabetical order. For example, enumerate is both a builtin and a function in the threading module. However, since builtins comes first alphabetically, it will take priority
md = "`enumerate`, `builtins.enumerate` and `threading.enumerate`"
NbdevLookup(('nbdev_stdlib')).linkify(md)'[`enumerate`](https://docs.python.org/3/library/functions.html#enumerate), [`builtins.enumerate`](https://docs.python.org/3/library/functions.html#enumerate) and [`threading.enumerate`](https://docs.python.org/3/library/threading.html#threading.enumerate)'
We can also take the find() function as another instance, it exists as a standard library and in numpy. Therefore, depending on the order of stripped libraries we pass, find() will link to either numpy or standard library.
md = "`find()`"
NbdevLookup(('nbdev_numpy','nbdev_stdlib')).linkify(md)'[`find()`](https://numpy.org/doc/stable/reference/generated/numpy.char.find.html#numpy.char.find)'
md = "`find()`"
NbdevLookup(('nbdev_stdlib','nbdev_numpy')).linkify(md)'[`find()`](https://docs.python.org/3/library/gettext.html#gettext.find)'
You can also use NbdevLookup with import aliases like the following:
import numpy as npNbdevLookup(ns=globals()).linkify('this is an aliased import link `np.array`')'this is an aliased import link [`np.array`](https://numpy.org/doc/stable/reference/generated/numpy.array.html#numpy.array)'