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

Update pylint, black &c. versions. Use flake8-bugbear style plugin #1162

Merged
merged 4 commits into from
Aug 29, 2023
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
12 changes: 9 additions & 3 deletions .pre-commit-config.yaml
Original file line number Diff line number Diff line change
@@ -1,17 +1,23 @@
repos:
- repo: https://github.com/ambv/black
rev: "22.12.0"
rev: "23.7.0"
hooks:
- id: black
- repo: https://github.com/asottile/reorder_python_imports
rev: "v3.9.0"
rev: "v3.10.0"
hooks:
- id: reorder-python-imports
- repo: https://github.com/pycqa/flake8
rev: "6.0.0"
rev: "6.1.0"
hooks:
- id: flake8
language_version: python3
additional_dependencies:
# NB: autoupdate does not pick up flake8-bugbear since it is a
# transitive dependency. Make sure to update flake8-bugbear
# manually on a regular basis.
- flake8-bugbear==23.7.10

- repo: local
hooks:
- id: eslint
Expand Down
4 changes: 2 additions & 2 deletions lektor/admin/modules/api.py
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ def _deserialize(
value: str,
attr: Optional[str],
data: Optional[Mapping[str, Any]],
**kwargs: Any
**kwargs: Any,
) -> ServerInfo:
lektor_config = self.context["lektor_config"]
server_id = super()._deserialize(value, attr, data, **kwargs)
Expand Down Expand Up @@ -439,7 +439,7 @@ def trigger_clean(ctx: LektorContext) -> Response:

@dataclass
class _PublishBuildParams:
server_info: ServerInfo = field(metadata=dict(data_key="server"))
server_info: ServerInfo = field(metadata={"data_key": "server"})


@bp.route("/publish")
Expand Down
2 changes: 1 addition & 1 deletion lektor/builder.py
Original file line number Diff line number Diff line change
Expand Up @@ -558,7 +558,7 @@ def checksum(self):
break
h.update(chunk)
checksum = h.hexdigest()
except (OSError, IOError):
except OSError:
checksum = "0" * 40
self._checksum = checksum
return checksum
Expand Down
1 change: 0 additions & 1 deletion lektor/cli_utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,6 @@ def extraflag(cli):


class AliasedGroup(click.Group):

# pylint: disable=inconsistent-return-statements
def get_command(self, ctx, cmd_name):
rv = click.Group.get_command(self, ctx, cmd_name)
Expand Down
2 changes: 1 addition & 1 deletion lektor/databags.py
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ def load_databag(filename):
return decode_flat_data(IniFile(filename).items(), dict_cls=OrderedDict)
else:
return None
except (OSError, IOError) as e:
except OSError as e:
if e.errno != errno.ENOENT:
raise
return None
Expand Down
78 changes: 39 additions & 39 deletions lektor/datamodel.py
Original file line number Diff line number Diff line change
Expand Up @@ -476,48 +476,48 @@ def _parse_order(value):
return None
return [x for x in [x.strip() for x in value.strip().split(",")] if x]

return dict(
filename=inifile.filename,
id=id,
parent=inifile.get("model.inherits"),
name_i18n=get_i18n_block(inifile, "model.name"),
label_i18n=get_i18n_block(inifile, "model.label"),
primary_field=inifile.get("model.primary_field"),
hidden=inifile.get_bool("model.hidden", default=None),
protected=inifile.get_bool("model.protected", default=None),
child_config=dict(
enabled=inifile.get_bool("children.enabled", default=None),
slug_format=inifile.get("children.slug_format"),
model=inifile.get("children.model"),
order_by=_parse_order(inifile.get("children.order_by")),
replaced_with=inifile.get("children.replaced_with"),
hidden=inifile.get_bool("children.hidden", default=None),
),
attachment_config=dict(
enabled=inifile.get_bool("attachments.enabled", default=None),
model=inifile.get("attachments.model"),
order_by=_parse_order(inifile.get("attachments.order_by")),
hidden=inifile.get_bool("attachments.hidden", default=None),
),
pagination_config=dict(
enabled=inifile.get_bool("pagination.enabled", default=None),
per_page=inifile.get_int("pagination.per_page"),
url_suffix=inifile.get("pagination.url_suffix"),
items=inifile.get("pagination.items"),
),
fields=fielddata_from_ini(inifile),
)
return {
"filename": inifile.filename,
"id": id,
"parent": inifile.get("model.inherits"),
"name_i18n": get_i18n_block(inifile, "model.name"),
"label_i18n": get_i18n_block(inifile, "model.label"),
"primary_field": inifile.get("model.primary_field"),
"hidden": inifile.get_bool("model.hidden", default=None),
"protected": inifile.get_bool("model.protected", default=None),
"child_config": {
"enabled": inifile.get_bool("children.enabled", default=None),
"slug_format": inifile.get("children.slug_format"),
"model": inifile.get("children.model"),
"order_by": _parse_order(inifile.get("children.order_by")),
"replaced_with": inifile.get("children.replaced_with"),
"hidden": inifile.get_bool("children.hidden", default=None),
},
"attachment_config": {
"enabled": inifile.get_bool("attachments.enabled", default=None),
"model": inifile.get("attachments.model"),
"order_by": _parse_order(inifile.get("attachments.order_by")),
"hidden": inifile.get_bool("attachments.hidden", default=None),
},
"pagination_config": {
"enabled": inifile.get_bool("pagination.enabled", default=None),
"per_page": inifile.get_int("pagination.per_page"),
"url_suffix": inifile.get("pagination.url_suffix"),
"items": inifile.get("pagination.items"),
},
"fields": fielddata_from_ini(inifile),
}


def flowblock_data_from_ini(id, inifile):
return dict(
filename=inifile.filename,
id=id,
name_i18n=get_i18n_block(inifile, "block.name"),
fields=fielddata_from_ini(inifile),
order=inifile.get_int("block.order"),
button_label=inifile.get("block.button_label"),
)
return {
"filename": inifile.filename,
"id": id,
"name_i18n": get_i18n_block(inifile, "block.name"),
"fields": fielddata_from_ini(inifile),
"order": inifile.get_int("block.order"),
"button_label": inifile.get("block.button_label"),
}


def fields_from_data(env, data, parent_fields=None):
Expand Down
11 changes: 5 additions & 6 deletions lektor/db.py
Original file line number Diff line number Diff line change
Expand Up @@ -1469,12 +1469,11 @@ def get_implied_datamodel(
"""Looks up a datamodel based on the information about the parent
of a model.
"""
dm_name = datamodel
model = datamodel

# Only look for a datamodel if there was not defined.
if dm_name is None:
if model is None:
parent = posixpath.dirname(path)
dm_name = None

# If we hit the root, and there is no model defined we need
# to make sure we do not recurse onto ourselves.
Expand All @@ -1484,11 +1483,11 @@ def get_implied_datamodel(
parent_obj = pad.get(parent)
if parent_obj is not None:
if is_attachment:
dm_name = parent_obj.datamodel.attachment_config.model
model = parent_obj.datamodel.attachment_config.model
else:
dm_name = parent_obj.datamodel.child_config.model
model = parent_obj.datamodel.child_config.model

for dm_name in _iter_datamodel_choices(dm_name, path, is_attachment):
for dm_name in _iter_datamodel_choices(model, path, is_attachment):
# If that datamodel exists, let's roll with it.
datamodel = self.datamodels.get(dm_name)
if datamodel is not None:
Expand Down
6 changes: 3 additions & 3 deletions lektor/editor.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
from collections.abc import Mapping
from collections.abc import MutableMapping
from collections.abc import ValuesView
from contextlib import suppress
from functools import wraps
from itertools import chain

Expand Down Expand Up @@ -116,6 +117,7 @@ def wrapper(self, *args, **kwargs):
f"EditorSession.{name} has been deprecated as of Lektor 3.3.2. "
f"Please use EditorSession.data.{newname} instead.",
DeprecationWarning,
stacklevel=2,
)
return wrapped(self, *args, **kwargs)

Expand Down Expand Up @@ -305,10 +307,8 @@ def _page_delete_impl(self):
directory = os.path.dirname(self.fs_path)

if self._recursive_delete:
try:
with suppress(OSError):
shutil.rmtree(directory)
except (OSError, IOError):
pass
return
if self._master_delete:
raise BadDelete(
Expand Down
7 changes: 6 additions & 1 deletion lektor/environment/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,7 @@ def _prevent_inlining(wrapped):

Applying this decorator to them will ensure they are not inlined.
"""

# the use of @pass_context will prevent inlining
@jinja2.pass_context
def wrapper(_jinja_ctx, *args, **kwargs):
Expand Down Expand Up @@ -222,11 +223,15 @@ def __init__(self, project, load_plugins=True, extra_flags=None):

from lektor.db import F, get_alts # pylint: disable=import-outside-toplevel

def latlongformat(latlong, secs=True):
lat, lon = latlong
return format_lat_long(lat=lat, long=lon, secs=secs)

self.jinja_env.filters.update(
tojson=tojson_filter,
latformat=lambda x, secs=True: format_lat_long(lat=x, secs=secs),
longformat=lambda x, secs=True: format_lat_long(long=x, secs=secs),
latlongformat=lambda x, secs=True: format_lat_long(secs=secs, *x),
latlongformat=latlongformat,
url=_prevent_inlining(url_to),
asseturl=_prevent_inlining(get_asset_url),
markdown=_markdown_filter,
Expand Down
2 changes: 1 addition & 1 deletion lektor/filecontents.py
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ def mimetype(self):
def bytes(self):
try:
return os.stat(self.filename).st_size
except (OSError, IOError):
except OSError:
return 0

def as_data_url(self, mediatype=None):
Expand Down
8 changes: 6 additions & 2 deletions lektor/imagetools.py
Original file line number Diff line number Diff line change
Expand Up @@ -378,6 +378,10 @@ def get_svg_info(fp):
)


class BadImageFile(Exception):
"""Raised when an image file can not be decoded."""


def get_image_info(fp):
"""Reads some image info from a file descriptor."""
head = fp.read(32)
Expand Down Expand Up @@ -416,7 +420,7 @@ def get_image_info(fp):
# "All markers are assigned two-byte codes: an X’FF’ byte
# followed by a byte which is not equal to 0 or X’FF’."
if not byte or ord(byte) != 0xFF:
raise Exception("Malformed JPEG image.")
raise BadImageFile("Malformed JPEG image.")

# "Any marker may optionally be preceded by any number
# of fill bytes, which are bytes assigned code X’FF’."
Expand All @@ -442,7 +446,7 @@ def get_image_info(fp):
#
# DNL is not supported by most applications,
# so we won't support it either.
raise Exception("JPEG with DNL not supported.")
raise BadImageFile("JPEG with DNL not supported.")

break

Expand Down
1 change: 1 addition & 0 deletions lektor/pluginsystem.py
Original file line number Diff line number Diff line change
Expand Up @@ -223,5 +223,6 @@ def emit(self, event, **kwargs):
"not break if new parameters are passed to it by newer "
"versions of Lektor.",
DeprecationWarning,
stacklevel=2,
)
return rv
2 changes: 1 addition & 1 deletion lektor/publisher.py
Original file line number Diff line number Diff line change
Expand Up @@ -592,7 +592,7 @@ def consolidate_listing(self, con, current_artifacts):
for artifact_name in current_artifacts.keys():
known_folders.add(posixpath.dirname(artifact_name))

for artifact_name, checksum in server_artifacts.items():
for artifact_name, _checksum in server_artifacts.items():
if artifact_name not in current_artifacts:
con.log_buffer.append("000 Deleting %s" % artifact_name)
con.delete_file(artifact_name)
Expand Down
16 changes: 8 additions & 8 deletions lektor/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
import uuid
import warnings
from contextlib import contextmanager
from contextlib import suppress
from dataclasses import dataclass
from datetime import datetime
from functools import lru_cache
Expand Down Expand Up @@ -420,7 +421,8 @@ def __new__(cls, value: str):
"Use the Url.from_string classmethod instead."
),
version="3.4.0",
)
),
stacklevel=2,
)
return cls.from_string(value)

Expand Down Expand Up @@ -533,18 +535,16 @@ def atomic_open(filename, mode="r", encoding=None):
f.close()
_exc_type, exc_value, tb = sys.exc_info()
if tmp_filename is not None:
try:
with suppress(OSError):
os.remove(tmp_filename)
except OSError:
pass

if exc_value.__traceback__ is not tb:
raise exc_value.with_traceback(tb) from e
raise exc_value from e
else:
f.close()
if tmp_filename is not None:
os.replace(tmp_filename, filename)

f.close()
if tmp_filename is not None:
os.replace(tmp_filename, filename)


def portable_popen(cmd, *args, **kwargs):
Expand Down
2 changes: 1 addition & 1 deletion tests/test_buildfailures.py
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,6 @@ def test_failure_controller_fs_exceptions(failure_controller):
failure_controller.clear_failure("broken")
with pytest.raises(OSError):
try:
assert False
raise RuntimeError("test exception")
except Exception:
failure_controller.store_failure("broken", sys.exc_info())
1 change: 0 additions & 1 deletion tests/test_db.py
Original file line number Diff line number Diff line change
Expand Up @@ -186,7 +186,6 @@ def test_undiscoverable_basics(pad):


def test_attachment_api(pad):

root = pad.root
root_attachments = [
"hello.txt",
Expand Down