Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Remove ipython genutils #1727

Merged
merged 3 commits into from Mar 11, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
2 changes: 1 addition & 1 deletion nbconvert/filters/__init__.py
Expand Up @@ -8,4 +8,4 @@
from .metadata import *
from .pandoc import *

from ipython_genutils.text import indent
from nbconvert.utils.text import indent
2 changes: 1 addition & 1 deletion nbconvert/nbconvertapp.py
Expand Up @@ -15,9 +15,9 @@
import glob
import asyncio
from textwrap import fill, dedent
from ipython_genutils.text import indent

from jupyter_core.application import JupyterApp, base_aliases, base_flags
from nbconvert.utils.text import indent
from traitlets.config import catch_config_error, Configurable
from traitlets import (
Unicode, List, Instance, DottedObjectName, Type, Bool,
Expand Down
82 changes: 82 additions & 0 deletions nbconvert/utils/io.py
Expand Up @@ -5,6 +5,10 @@
# Distributed under the terms of the Modified BSD License.

import codecs
import errno
import os
import random
import shutil
import sys

def unicode_std_stream(stream='stdout'):
Expand Down Expand Up @@ -48,3 +52,81 @@ def unicode_stdin_stream():
class FormatSafeDict(dict):
def __missing__(self, key):
return '{' + key + '}'


try:
ENOLINK = errno.ENOLINK
except AttributeError:
ENOLINK = 1998


def link(src, dst):
"""Hard links ``src`` to ``dst``, returning 0 or errno.

Note that the special errno ``ENOLINK`` will be returned if ``os.link`` isn't
supported by the operating system.
"""

if not hasattr(os, "link"):
return ENOLINK
link_errno = 0
try:
os.link(src, dst)
except OSError as e:
link_errno = e.errno
return link_errno


def link_or_copy(src, dst):
"""Attempts to hardlink ``src`` to ``dst``, copying if the link fails.

Attempts to maintain the semantics of ``shutil.copy``.

Because ``os.link`` does not overwrite files, a unique temporary file
will be used if the target already exists, then that file will be moved
into place.
"""

if os.path.isdir(dst):
dst = os.path.join(dst, os.path.basename(src))

link_errno = link(src, dst)
if link_errno == errno.EEXIST:
if os.stat(src).st_ino == os.stat(dst).st_ino:
# dst is already a hard link to the correct file, so we don't need
# to do anything else. If we try to link and rename the file
# anyway, we get duplicate files - see http://bugs.python.org/issue21876
return

new_dst = dst + "-temp-%04X" %(random.randint(1, 16**4), )
try:
link_or_copy(src, new_dst)
except:
try:
os.remove(new_dst)
except OSError:
pass
raise
os.rename(new_dst, dst)
elif link_errno != 0:
# Either link isn't supported, or the filesystem doesn't support
# linking, or 'src' and 'dst' are on different filesystems.
shutil.copy(src, dst)


def ensure_dir_exists(path, mode=0o755):
"""ensure that a directory exists

If it doesn't exist, try to create it and protect against a race condition
if another process is doing the same.

The default permissions are 755, which differ from os.makedirs default of 777.
"""
if not os.path.exists(path):
try:
os.makedirs(path, mode=mode)
except OSError as e:
if e.errno != errno.EEXIST:
raise
elif not os.path.isdir(path):
raise IOError("%r exists but is not a directory" % path)
41 changes: 41 additions & 0 deletions nbconvert/utils/text.py
@@ -0,0 +1,41 @@
import os
import re


def indent(instr, nspaces=4, ntabs=0, flatten=False):
"""Indent a string a given number of spaces or tabstops.

indent(str,nspaces=4,ntabs=0) -> indent str by ntabs+nspaces.

Parameters
----------

instr : basestring
The string to be indented.
nspaces : int (default: 4)
The number of spaces to be indented.
ntabs : int (default: 0)
The number of tabs to be indented.
flatten : bool (default: False)
Whether to scrub existing indentation. If True, all lines will be
aligned to the same indentation. If False, existing indentation will
be strictly increased.

Returns
-------

str|unicode : string indented by ntabs and nspaces.

"""
if instr is None:
return
ind = '\t' * ntabs + ' ' * nspaces
if flatten:
pat = re.compile(r'^\s*', re.MULTILINE)
else:
pat = re.compile(r'^', re.MULTILINE)
outstr = re.sub(pat, ind, instr)
if outstr.endswith(os.linesep + ind):
return outstr[:-len(ind)]
else:
return outstr
4 changes: 3 additions & 1 deletion nbconvert/writers/files.py
Expand Up @@ -8,8 +8,10 @@
import glob

from pathlib import Path

from nbconvert.utils.io import ensure_dir_exists, link_or_copy
from traitlets import Unicode, observe
from ipython_genutils.path import link_or_copy, ensure_dir_exists


from .base import WriterBase

Expand Down