You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
masque/masque/file/utils.py

82 lines
1.9 KiB
Python

"""
Helper functions for file reading and writing
"""
from typing import Union, IO, Iterator
import re
import pathlib
1 year ago
import logging
import tempfile
import shutil
from contextlib import contextmanager
from .. import Pattern, PatternError
from ..shapes import Polygon, Path
1 year ago
logger = logging.getLogger(__name__)
def mangle_name(name: str) -> str:
"""
Sanitize a name.
Args:
name: Name we want to mangle.
Returns:
Mangled name.
"""
expression = re.compile(r'[^A-Za-z0-9_\?\$]')
sanitized_name = expression.sub('_', name)
return sanitized_name
def clean_pattern_vertices(pat: Pattern) -> Pattern:
"""
Given a pattern, remove any redundant vertices in its polygons and paths.
The cleaning process completely removes any polygons with zero area or <3 vertices.
Args:
pat: Pattern to clean
Returns:
pat
"""
remove_inds = []
for ii, shape in enumerate(pat.shapes):
if not isinstance(shape, (Polygon, Path)):
continue
try:
shape.clean_vertices()
except PatternError:
remove_inds.append(ii)
for ii in sorted(remove_inds, reverse=True):
del pat.shapes[ii]
return pat
def is_gzipped(path: pathlib.Path) -> bool:
with open(path, 'rb') as stream:
magic_bytes = stream.read(2)
return magic_bytes == b'\x1f\x8b'
@contextmanager
def tmpfile(path: Union[str, pathlib.Path]) -> Iterator[IO[bytes]]:
"""
Context manager which allows you to write to a temporary file,
and move that file into its final location only after the write
has finished.
"""
path = pathlib.Path(path)
suffixes = ''.join(path.suffixes)
with tempfile.NamedTemporaryFile(suffix=suffixes, delete=False) as tmp_stream:
yield tmp_stream
try:
shutil.move(tmp_stream.name, path)
finally:
pathlib.Path(tmp_stream.name).unlink(missing_ok=True)