Compare commits
20 Commits
014c7191cd
...
develop
Author | SHA1 | Date | |
---|---|---|---|
3b6f8ca28b | |||
2a59ec4cbd | |||
49a788425e | |||
75d14dde6c | |||
213cd6f7b0 | |||
9031295b4d | |||
69997979c3 | |||
7e0679e872 | |||
4adb943a56 | |||
0812d67919 | |||
3105eee488 | |||
624b64d6ca | |||
3012d36866 | |||
1aa1a6d6b7 | |||
16d362da8a | |||
32f8cb0f22 | |||
0a17bbc0d9 | |||
7694a3e2fd | |||
d3b11d6361 | |||
29e6068db2 |
@ -1,4 +1,4 @@
|
|||||||
FROM python:3.12.1-bookworm
|
FROM python:3.9-bookworm
|
||||||
LABEL maintainer="AJ Slater <aj@slater.net>"
|
LABEL maintainer="AJ Slater <aj@slater.net>"
|
||||||
|
|
||||||
COPY debian.sources /etc/apt/sources.list.d/
|
COPY debian.sources /etc/apt/sources.list.d/
|
||||||
@ -14,7 +14,7 @@ RUN apt-get clean \
|
|||||||
WORKDIR /app
|
WORKDIR /app
|
||||||
|
|
||||||
COPY bin ./bin
|
COPY bin ./bin
|
||||||
COPY package.json package-lock.json pyproject.toml poetry.lock Makefile ./
|
COPY .eslintignore .gitignore .prettierignore .remarkignore .shellcheckrc eslint.config.js package.json package-lock.json pyproject.toml poetry.lock Makefile ./
|
||||||
RUN make install-all
|
RUN make install-all
|
||||||
|
|
||||||
COPY . .
|
COPY . .
|
||||||
|
9
NEWS.md
9
NEWS.md
@ -1,14 +1,19 @@
|
|||||||
# 📰 comicfn2dict News
|
# 📰 comicfn2dict News
|
||||||
|
|
||||||
|
## v0.2.1
|
||||||
|
|
||||||
|
- Support Python 3.9, thanks to @lordwelch
|
||||||
|
|
||||||
## v0.2.0
|
## v0.2.0
|
||||||
|
|
||||||
|
- The `-` character no longer breaks up tokens
|
||||||
- Titles are now parsed only if they occur after the series token AND after
|
- Titles are now parsed only if they occur after the series token AND after
|
||||||
either issue, year or volume.
|
either issue, year or volume.
|
||||||
- A more sophisticated date parser.
|
- A more sophisticated date parser.
|
||||||
- Issue numbers that lead with a '#' character may start with alphabetical
|
- Issue numbers that lead with a '#' character may start with alphabetical
|
||||||
characters.
|
characters.
|
||||||
- If volume is parsed, but issue number is not, the issue number is copied from
|
- If volume exists, but issue number does not, then issue number becomes the
|
||||||
the volume number.
|
volume number.
|
||||||
- ComicFilenameParser and ComicFilenameSerializer classes are available as well
|
- ComicFilenameParser and ComicFilenameSerializer classes are available as well
|
||||||
as the old function API.
|
as the old function API.
|
||||||
- New test cases thanks to @lordwelch & @bpepple
|
- New test cases thanks to @lordwelch & @bpepple
|
||||||
|
@ -10,7 +10,7 @@ bin/sortignore.sh
|
|||||||
####################
|
####################
|
||||||
###### Python ######
|
###### Python ######
|
||||||
###################
|
###################
|
||||||
poetry run ruff --fix .
|
poetry run ruff check --fix .
|
||||||
poetry run ruff format .
|
poetry run ruff format .
|
||||||
# poetry run djlint templates --profile=django --reformat
|
# poetry run djlint templates --profile=django --reformat
|
||||||
|
|
||||||
|
@ -5,7 +5,7 @@ set -euxo pipefail
|
|||||||
####################
|
####################
|
||||||
###### Python ######
|
###### Python ######
|
||||||
####################
|
####################
|
||||||
poetry run ruff .
|
poetry run ruff check .
|
||||||
poetry run ruff format --check .
|
poetry run ruff format --check .
|
||||||
poetry run pyright
|
poetry run pyright
|
||||||
poetry run vulture .
|
poetry run vulture .
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
"""Comic Filename to Dict parser and unparser."""
|
"""Comic Filename to Dict parser and unparser."""
|
||||||
|
|
||||||
from .parse import ComicFilenameParser, comicfn2dict # noqa: F401
|
from .parse import ComicFilenameParser, comicfn2dict # noqa: F401
|
||||||
from .unparse import ComicFilenameSerializer, dict2comicfn # noqa: F401
|
from .unparse import ComicFilenameSerializer, dict2comicfn # noqa: F401
|
||||||
|
@ -1,12 +1,14 @@
|
|||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
"""Simple cli for comicfn2dict."""
|
"""Simple cli for comicfn2dict."""
|
||||||
|
|
||||||
from argparse import ArgumentParser
|
from argparse import ArgumentParser
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from pprint import pprint
|
from pprint import pprint
|
||||||
|
|
||||||
from comicfn2dict.parse import ComicFilenameParser
|
from comicfn2dict.parse import ComicFilenameParser
|
||||||
|
|
||||||
|
|
||||||
def main():
|
def main() -> None:
|
||||||
"""Test parser."""
|
"""Test parser."""
|
||||||
description = "Comic book archive read/write tool."
|
description = "Comic book archive read/write tool."
|
||||||
parser = ArgumentParser(description=description)
|
parser = ArgumentParser(description=description)
|
||||||
@ -23,7 +25,7 @@ def main():
|
|||||||
cfnparser = ComicFilenameParser(name, verbose=args.verbose)
|
cfnparser = ComicFilenameParser(name, verbose=args.verbose)
|
||||||
metadata = cfnparser.parse()
|
metadata = cfnparser.parse()
|
||||||
if args.verbose:
|
if args.verbose:
|
||||||
print("=" * 80)
|
print("=" * 80) # noqa:T201
|
||||||
pprint(metadata) # noqa:T203
|
pprint(metadata) # noqa:T203
|
||||||
|
|
||||||
|
|
||||||
|
@ -6,4 +6,4 @@ def print_log_header(label: str) -> None:
|
|||||||
prefix = "-" * 3 + label
|
prefix = "-" * 3 + label
|
||||||
suffix_len = 80 - len(prefix)
|
suffix_len = 80 - len(prefix)
|
||||||
suffix = "-" * suffix_len
|
suffix = "-" * suffix_len
|
||||||
print(prefix + suffix)
|
print(prefix + suffix) # noqa: T201
|
||||||
|
@ -1,10 +1,14 @@
|
|||||||
"""Parse comic book archive names using the simple 'parse' parser."""
|
"""Parse comic book archive names using the simple 'parse' parser."""
|
||||||
from pprint import pformat
|
|
||||||
|
from __future__ import annotations
|
||||||
|
|
||||||
from calendar import month_abbr
|
from calendar import month_abbr
|
||||||
from copy import copy
|
from copy import copy
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from re import Match, Pattern
|
from pprint import pformat
|
||||||
from typing import Any
|
from sys import maxsize
|
||||||
|
from typing import TYPE_CHECKING
|
||||||
|
|
||||||
from comicfn2dict.log import print_log_header
|
from comicfn2dict.log import print_log_header
|
||||||
from comicfn2dict.regex import (
|
from comicfn2dict.regex import (
|
||||||
ALPHA_MONTH_RANGE_RE,
|
ALPHA_MONTH_RANGE_RE,
|
||||||
@ -18,8 +22,8 @@ from comicfn2dict.regex import (
|
|||||||
ORIGINAL_FORMAT_SCAN_INFO_RE,
|
ORIGINAL_FORMAT_SCAN_INFO_RE,
|
||||||
ORIGINAL_FORMAT_SCAN_INFO_SEPARATE_RE,
|
ORIGINAL_FORMAT_SCAN_INFO_SEPARATE_RE,
|
||||||
PUBLISHER_AMBIGUOUS_RE,
|
PUBLISHER_AMBIGUOUS_RE,
|
||||||
PUBLISHER_UNAMBIGUOUS_RE,
|
|
||||||
PUBLISHER_AMBIGUOUS_TOKEN_RE,
|
PUBLISHER_AMBIGUOUS_TOKEN_RE,
|
||||||
|
PUBLISHER_UNAMBIGUOUS_RE,
|
||||||
PUBLISHER_UNAMBIGUOUS_TOKEN_RE,
|
PUBLISHER_UNAMBIGUOUS_TOKEN_RE,
|
||||||
REGEX_SUBS,
|
REGEX_SUBS,
|
||||||
REMAINING_GROUP_RE,
|
REMAINING_GROUP_RE,
|
||||||
@ -32,42 +36,43 @@ from comicfn2dict.regex import (
|
|||||||
YEAR_TOKEN_RE,
|
YEAR_TOKEN_RE,
|
||||||
)
|
)
|
||||||
|
|
||||||
_REMAINING_GROUP_KEYS = ("series", "title")
|
if TYPE_CHECKING:
|
||||||
_TITLE_PRECEDING_KEYS = ("issue", "year", "volume")
|
from re import Match, Pattern
|
||||||
|
|
||||||
_DATE_KEYS = frozenset({"year", "month", "day"})
|
_DATE_KEYS = frozenset({"year", "month", "day"})
|
||||||
|
_REMAINING_GROUP_KEYS = ("series", "title")
|
||||||
|
# Ordered by commonness.
|
||||||
|
_TITLE_PRECEDING_KEYS = ("issue", "year", "volume", "month")
|
||||||
|
|
||||||
|
|
||||||
class ComicFilenameParser:
|
class ComicFilenameParser:
|
||||||
"""Parse a filename metadata into a dict."""
|
"""Parse a filename metadata into a dict."""
|
||||||
|
|
||||||
def path_index(self, key: str):
|
def path_index(self, key: str, default: int = -1) -> int:
|
||||||
"""Lazily retrieve and memoize the key's location in the path."""
|
"""Lazily retrieve and memoize the key's location in the path."""
|
||||||
if key == "remainders":
|
if key == "remainders":
|
||||||
return -1
|
return default
|
||||||
value: str = self.metadata.get(key, "") # type: ignore
|
value: str = self.metadata.get(key, "") # type: ignore
|
||||||
if not value:
|
if not value:
|
||||||
return -1
|
return default
|
||||||
if value not in self._path_indexes:
|
if value not in self._path_indexes:
|
||||||
# XXX This is fragile, but it's difficult to calculate the original
|
# XXX This is fragile, but it's difficult to calculate the original
|
||||||
# position at match time from the ever changing _unparsed_path.
|
# position at match time from the ever changing _unparsed_path.
|
||||||
if key == "ext":
|
index = self.path.rfind(value) if key == "ext" else self.path.find(value)
|
||||||
index = self.path.rfind(value)
|
|
||||||
else:
|
|
||||||
index = self.path.find(value)
|
|
||||||
self._path_indexes[value] = index
|
self._path_indexes[value] = index
|
||||||
return self._path_indexes[value]
|
return self._path_indexes[value]
|
||||||
|
|
||||||
def _log(self, label):
|
def _log(self, label: str) -> None:
|
||||||
if not self._debug:
|
if not self._debug:
|
||||||
return
|
return
|
||||||
print_log_header(label)
|
print_log_header(label)
|
||||||
combined = {}
|
combined = {}
|
||||||
for key in self.metadata:
|
for key in self.metadata:
|
||||||
combined[key] = (self.metadata.get(key), self.path_index(key))
|
combined[key] = (self.metadata.get(key), self.path_index(key))
|
||||||
print(" " + self._unparsed_path)
|
print(" " + self._unparsed_path) # noqa: T201
|
||||||
print(" " + pformat(combined))
|
print(" " + pformat(combined)) # noqa: T201
|
||||||
|
|
||||||
def _parse_ext(self):
|
def _parse_ext(self) -> None:
|
||||||
"""Pop the extension from the pathname."""
|
"""Pop the extension from the pathname."""
|
||||||
path = Path(self._unparsed_path)
|
path = Path(self._unparsed_path)
|
||||||
suffix = path.suffix
|
suffix = path.suffix
|
||||||
@ -79,7 +84,7 @@ class ComicFilenameParser:
|
|||||||
self.metadata["ext"] = ext
|
self.metadata["ext"] = ext
|
||||||
self._unparsed_path = data
|
self._unparsed_path = data
|
||||||
|
|
||||||
def _clean_dividers(self):
|
def _clean_dividers(self) -> None:
|
||||||
"""Replace non space dividers and clean extra spaces out of string."""
|
"""Replace non space dividers and clean extra spaces out of string."""
|
||||||
data = self._unparsed_path
|
data = self._unparsed_path
|
||||||
|
|
||||||
@ -120,7 +125,7 @@ class ComicFilenameParser:
|
|||||||
parts.append(token)
|
parts.append(token)
|
||||||
self._unparsed_path = TOKEN_DELIMETER.join(parts)
|
self._unparsed_path = TOKEN_DELIMETER.join(parts)
|
||||||
|
|
||||||
def _parse_items(
|
def _parse_items( # noqa: PLR0913
|
||||||
self,
|
self,
|
||||||
regex: Pattern,
|
regex: Pattern,
|
||||||
require_all: bool = False,
|
require_all: bool = False,
|
||||||
@ -142,21 +147,21 @@ class ComicFilenameParser:
|
|||||||
if pop:
|
if pop:
|
||||||
self._parse_items_pop_tokens(regex, first_only)
|
self._parse_items_pop_tokens(regex, first_only)
|
||||||
|
|
||||||
def _parse_issue(self):
|
def _parse_issue(self) -> None:
|
||||||
"""Parse Issue."""
|
"""Parse Issue."""
|
||||||
self._parse_items(ISSUE_NUMBER_RE)
|
self._parse_items(ISSUE_NUMBER_RE)
|
||||||
if "issue" not in self.metadata:
|
if "issue" not in self.metadata:
|
||||||
self._parse_items(ISSUE_WITH_COUNT_RE)
|
self._parse_items(ISSUE_WITH_COUNT_RE)
|
||||||
self._log("After Issue")
|
self._log("After Issue")
|
||||||
|
|
||||||
def _parse_volume(self):
|
def _parse_volume(self) -> None:
|
||||||
"""Parse Volume."""
|
"""Parse Volume."""
|
||||||
self._parse_items(VOLUME_RE)
|
self._parse_items(VOLUME_RE)
|
||||||
if "volume" not in self.metadata:
|
if "volume" not in self.metadata:
|
||||||
self._parse_items(VOLUME_WITH_COUNT_RE)
|
self._parse_items(VOLUME_WITH_COUNT_RE)
|
||||||
self._log("After Volume")
|
self._log("After Volume")
|
||||||
|
|
||||||
def _alpha_month_to_numeric(self):
|
def _alpha_month_to_numeric(self) -> None:
|
||||||
"""Translate alpha_month to numeric month."""
|
"""Translate alpha_month to numeric month."""
|
||||||
if alpha_month := self.metadata.pop("alpha_month", ""):
|
if alpha_month := self.metadata.pop("alpha_month", ""):
|
||||||
alpha_month = alpha_month.capitalize() # type: ignore
|
alpha_month = alpha_month.capitalize() # type: ignore
|
||||||
@ -166,7 +171,7 @@ class ComicFilenameParser:
|
|||||||
self.metadata["month"] = month
|
self.metadata["month"] = month
|
||||||
break
|
break
|
||||||
|
|
||||||
def _parse_dates(self):
|
def _parse_dates(self) -> None:
|
||||||
"""Parse date schemes."""
|
"""Parse date schemes."""
|
||||||
# Discard second month of alpha month ranges.
|
# Discard second month of alpha month ranges.
|
||||||
self._unparsed_path = ALPHA_MONTH_RANGE_RE.sub(r"\1", self._unparsed_path)
|
self._unparsed_path = ALPHA_MONTH_RANGE_RE.sub(r"\1", self._unparsed_path)
|
||||||
@ -192,9 +197,8 @@ class ComicFilenameParser:
|
|||||||
self.metadata["volume"] = volume
|
self.metadata["volume"] = volume
|
||||||
self._log("After Date")
|
self._log("After Date")
|
||||||
|
|
||||||
def _parse_format_and_scan_info(self):
|
def _parse_format_and_scan_info(self) -> None:
|
||||||
# Format & Scan Info
|
"""Format & Scan Info."""
|
||||||
#
|
|
||||||
self._parse_items(
|
self._parse_items(
|
||||||
ORIGINAL_FORMAT_SCAN_INFO_RE,
|
ORIGINAL_FORMAT_SCAN_INFO_RE,
|
||||||
require_all=True,
|
require_all=True,
|
||||||
@ -231,7 +235,7 @@ class ComicFilenameParser:
|
|||||||
self._parse_items(ISSUE_BEGIN_RE)
|
self._parse_items(ISSUE_BEGIN_RE)
|
||||||
self._log("After Issue on ends of tokens")
|
self._log("After Issue on ends of tokens")
|
||||||
|
|
||||||
def _parse_publisher(self):
|
def _parse_publisher(self) -> None:
|
||||||
"""Parse Publisher."""
|
"""Parse Publisher."""
|
||||||
# Pop single tokens so they don't end up titles.
|
# Pop single tokens so they don't end up titles.
|
||||||
self._parse_items(PUBLISHER_UNAMBIGUOUS_TOKEN_RE, first_only=True)
|
self._parse_items(PUBLISHER_UNAMBIGUOUS_TOKEN_RE, first_only=True)
|
||||||
@ -243,15 +247,19 @@ class ComicFilenameParser:
|
|||||||
self._parse_items(PUBLISHER_AMBIGUOUS_RE, pop=False, first_only=True)
|
self._parse_items(PUBLISHER_AMBIGUOUS_RE, pop=False, first_only=True)
|
||||||
self._log("After publisher")
|
self._log("After publisher")
|
||||||
|
|
||||||
def _is_title_in_position(self, value):
|
def _is_at_title_position(self, value: str) -> bool:
|
||||||
"""Does the title come after series and one other token if they exist."""
|
"""Title is in correct position."""
|
||||||
title_index = self.path.find(value)
|
title_index = self.path.find(value)
|
||||||
|
|
||||||
# Does a series come first.
|
# Titles must come after series but before format and scan_info
|
||||||
if title_index < self.path_index("series"):
|
if (
|
||||||
|
title_index < self.path_index("series")
|
||||||
|
or title_index > self.path_index("original_format", maxsize)
|
||||||
|
or title_index > self.path_index("scan_info", maxsize)
|
||||||
|
):
|
||||||
return False
|
return False
|
||||||
|
|
||||||
# If other tokens exist then they much precede the title.
|
# Titles must be after the series and one other token.
|
||||||
title_ok = False
|
title_ok = False
|
||||||
other_tokens_exist = False
|
other_tokens_exist = False
|
||||||
for preceding_key in _TITLE_PRECEDING_KEYS:
|
for preceding_key in _TITLE_PRECEDING_KEYS:
|
||||||
@ -270,7 +278,27 @@ class ComicFilenameParser:
|
|||||||
value = value.strip("'").strip()
|
value = value.strip("'").strip()
|
||||||
return value.strip('"').strip()
|
return value.strip('"').strip()
|
||||||
|
|
||||||
def _parse_series_and_title(self):
|
def _parse_series_and_title_token(
|
||||||
|
self, remaining_key_index: int, tokens: list[str]
|
||||||
|
) -> str:
|
||||||
|
"""Parse one series or title token."""
|
||||||
|
key = _REMAINING_GROUP_KEYS[remaining_key_index]
|
||||||
|
if key in self.metadata:
|
||||||
|
return ""
|
||||||
|
token = tokens.pop(0)
|
||||||
|
match = REMAINING_GROUP_RE.search(token)
|
||||||
|
if not match:
|
||||||
|
return token
|
||||||
|
value = match.group()
|
||||||
|
if key == "title" and not self._is_at_title_position(value):
|
||||||
|
return token
|
||||||
|
value = NON_NUMBER_DOT_RE.sub(r"\1 \2", value)
|
||||||
|
value = self._grouping_operators_strip(value)
|
||||||
|
if value:
|
||||||
|
self.metadata[key] = value
|
||||||
|
return ""
|
||||||
|
|
||||||
|
def _parse_series_and_title(self) -> None:
|
||||||
"""Assign series and title."""
|
"""Assign series and title."""
|
||||||
if not self._unparsed_path:
|
if not self._unparsed_path:
|
||||||
return
|
return
|
||||||
@ -279,28 +307,17 @@ class ComicFilenameParser:
|
|||||||
unused_tokens = []
|
unused_tokens = []
|
||||||
tokens = self._unparsed_path.split(TOKEN_DELIMETER)
|
tokens = self._unparsed_path.split(TOKEN_DELIMETER)
|
||||||
while tokens and remaining_key_index < len(_REMAINING_GROUP_KEYS):
|
while tokens and remaining_key_index < len(_REMAINING_GROUP_KEYS):
|
||||||
key = _REMAINING_GROUP_KEYS[remaining_key_index]
|
unused_token = self._parse_series_and_title_token(
|
||||||
if key in self.metadata:
|
remaining_key_index, tokens
|
||||||
continue
|
)
|
||||||
token = tokens.pop(0)
|
if unused_token:
|
||||||
match = REMAINING_GROUP_RE.search(token)
|
unused_tokens.append(unused_token)
|
||||||
if match:
|
remaining_key_index += 1
|
||||||
value = match.group()
|
|
||||||
if key == "title" and not self._is_title_in_position(value):
|
|
||||||
unused_tokens.append(token)
|
|
||||||
continue
|
|
||||||
value = self._grouping_operators_strip(value)
|
|
||||||
value = NON_NUMBER_DOT_RE.sub(r"\1 \2", value)
|
|
||||||
|
|
||||||
self.metadata[key] = value
|
|
||||||
remaining_key_index += 1
|
|
||||||
else:
|
|
||||||
unused_tokens.append(token)
|
|
||||||
|
|
||||||
self._unparsed_path = " ".join(unused_tokens) if unused_tokens else ""
|
self._unparsed_path = " ".join(unused_tokens) if unused_tokens else ""
|
||||||
self._log("After Series & Title")
|
self._log("After Series & Title")
|
||||||
|
|
||||||
def _add_remainders(self):
|
def _add_remainders(self) -> None:
|
||||||
"""Add Remainders."""
|
"""Add Remainders."""
|
||||||
remainders = []
|
remainders = []
|
||||||
for token in self._unparsed_path.split(TOKEN_DELIMETER):
|
for token in self._unparsed_path.split(TOKEN_DELIMETER):
|
||||||
@ -310,7 +327,7 @@ class ComicFilenameParser:
|
|||||||
if remainders:
|
if remainders:
|
||||||
self.metadata["remainders"] = tuple(remainders)
|
self.metadata["remainders"] = tuple(remainders)
|
||||||
|
|
||||||
def parse(self) -> dict[str, Any]:
|
def parse(self) -> dict[str, str | tuple[str, ...]]:
|
||||||
"""Parse the filename with a hierarchy of regexes."""
|
"""Parse the filename with a hierarchy of regexes."""
|
||||||
self._log("Init")
|
self._log("Init")
|
||||||
self._parse_ext()
|
self._parse_ext()
|
||||||
@ -345,7 +362,9 @@ class ComicFilenameParser:
|
|||||||
self._path_indexes: dict[str, int] = {}
|
self._path_indexes: dict[str, int] = {}
|
||||||
|
|
||||||
|
|
||||||
def comicfn2dict(path: str | Path, verbose: int = 0):
|
def comicfn2dict(
|
||||||
"""Simple API."""
|
path: str | Path, verbose: int = 0
|
||||||
|
) -> dict[str, str | tuple[str, ...]]:
|
||||||
|
"""Simplfily the API."""
|
||||||
parser = ComicFilenameParser(path, verbose=verbose)
|
parser = ComicFilenameParser(path, verbose=verbose)
|
||||||
return parser.parse()
|
return parser.parse()
|
||||||
|
@ -1,16 +1,9 @@
|
|||||||
"""Parsing regexes."""
|
"""Parsing regexes."""
|
||||||
import re
|
|
||||||
|
from re import IGNORECASE, Pattern, compile
|
||||||
from types import MappingProxyType
|
from types import MappingProxyType
|
||||||
|
|
||||||
|
PUBLISHERS_UNAMBIGUOUS: tuple[str, ...] = (
|
||||||
def re_compile(exp, parenthify=False):
|
|
||||||
"""Compile regex with options."""
|
|
||||||
if parenthify:
|
|
||||||
exp = r"\(" + exp + r"\)"
|
|
||||||
return re.compile(exp, flags=re.IGNORECASE)
|
|
||||||
|
|
||||||
|
|
||||||
PUBLISHERS_UNAMBIGUOUS = (
|
|
||||||
r"Abrams ComicArts",
|
r"Abrams ComicArts",
|
||||||
r"BOOM! Studios",
|
r"BOOM! Studios",
|
||||||
r"DC(\sComics)?",
|
r"DC(\sComics)?",
|
||||||
@ -26,15 +19,15 @@ PUBLISHERS_UNAMBIGUOUS = (
|
|||||||
r"SelfMadeHero",
|
r"SelfMadeHero",
|
||||||
r"Titan Comics",
|
r"Titan Comics",
|
||||||
)
|
)
|
||||||
PUBLISHERS_AMBIGUOUS = (
|
PUBLISHERS_AMBIGUOUS: tuple[str, ...] = (
|
||||||
r"Marvel",
|
r"(?<!Capt\.\s)(?<!Capt\s)(?<!Captain\s)Marvel",
|
||||||
r"Heavy Metal",
|
r"Heavy Metal",
|
||||||
r"Epic",
|
r"Epic",
|
||||||
r"Image",
|
r"Image",
|
||||||
r"Mirage",
|
r"Mirage",
|
||||||
)
|
)
|
||||||
|
|
||||||
ORIGINAL_FORMAT_PATTERNS = (
|
ORIGINAL_FORMAT_PATTERNS: tuple[str, ...] = (
|
||||||
r"Anthology",
|
r"Anthology",
|
||||||
r"(One|1)[-\s]Shot",
|
r"(One|1)[-\s]Shot",
|
||||||
r"Annual",
|
r"Annual",
|
||||||
@ -63,7 +56,7 @@ ORIGINAL_FORMAT_PATTERNS = (
|
|||||||
r"Web([-\s]?(Comic|Rip))?",
|
r"Web([-\s]?(Comic|Rip))?",
|
||||||
)
|
)
|
||||||
|
|
||||||
MONTHS = (
|
MONTHS: tuple[str, ...] = (
|
||||||
r"Jan(uary)?",
|
r"Jan(uary)?",
|
||||||
r"Feb(ruary)?",
|
r"Feb(ruary)?",
|
||||||
r"Mar(ch)?",
|
r"Mar(ch)?",
|
||||||
@ -78,7 +71,15 @@ MONTHS = (
|
|||||||
r"Dec(ember)?",
|
r"Dec(ember)?",
|
||||||
)
|
)
|
||||||
|
|
||||||
TOKEN_DELIMETER = r"/"
|
TOKEN_DELIMETER: str = r"/"
|
||||||
|
|
||||||
|
|
||||||
|
def re_compile(exp: str, parenthify: bool = False) -> Pattern:
|
||||||
|
"""Compile regex with options."""
|
||||||
|
if parenthify:
|
||||||
|
exp = r"\(" + exp + r"\)"
|
||||||
|
return compile(exp, flags=IGNORECASE)
|
||||||
|
|
||||||
|
|
||||||
# CLEAN
|
# CLEAN
|
||||||
_TOKEN_DIVIDERS_RE = re_compile(r":")
|
_TOKEN_DIVIDERS_RE = re_compile(r":")
|
||||||
@ -87,7 +88,7 @@ _EXTRA_SPACES_RE = re_compile(r"\s\s+")
|
|||||||
_LEFT_PAREN_EQUIVALENT_RE = re_compile(r"\[")
|
_LEFT_PAREN_EQUIVALENT_RE = re_compile(r"\[")
|
||||||
_RIGHT_PAREN_EQUIVALENT_RE = re_compile(r"\]")
|
_RIGHT_PAREN_EQUIVALENT_RE = re_compile(r"\]")
|
||||||
_DOUBLE_UNDERSCORE_RE = re_compile(r"__(.*)__")
|
_DOUBLE_UNDERSCORE_RE = re_compile(r"__(.*)__")
|
||||||
REGEX_SUBS: MappingProxyType[re.Pattern, tuple[str, int]] = MappingProxyType(
|
REGEX_SUBS: MappingProxyType[Pattern, tuple[str, int]] = MappingProxyType(
|
||||||
{
|
{
|
||||||
_DOUBLE_UNDERSCORE_RE: (r"(\1)", 0),
|
_DOUBLE_UNDERSCORE_RE: (r"(\1)", 0),
|
||||||
_TOKEN_DIVIDERS_RE: (TOKEN_DELIMETER, 1),
|
_TOKEN_DIVIDERS_RE: (TOKEN_DELIMETER, 1),
|
||||||
@ -104,7 +105,7 @@ _MONTH_ALPHA_RE_EXP = r"(" + "(?P<alpha_month>" + r"|".join(MONTHS) + r")\.?" r"
|
|||||||
_MONTH_NUMERIC_RE_EXP = r"(?P<month>0?\d|1[0-2]?)"
|
_MONTH_NUMERIC_RE_EXP = r"(?P<month>0?\d|1[0-2]?)"
|
||||||
_MONTH_RE_EXP = r"(" + _MONTH_ALPHA_RE_EXP + r"|" + _MONTH_NUMERIC_RE_EXP + r")"
|
_MONTH_RE_EXP = r"(" + _MONTH_ALPHA_RE_EXP + r"|" + _MONTH_NUMERIC_RE_EXP + r")"
|
||||||
_ALPHA_MONTH_RANGE = (
|
_ALPHA_MONTH_RANGE = (
|
||||||
r"\b"
|
r"\b" # noqa: ISC003
|
||||||
+ r"("
|
+ r"("
|
||||||
+ r"|".join(MONTHS)
|
+ r"|".join(MONTHS)
|
||||||
+ r")"
|
+ r")"
|
||||||
@ -115,7 +116,7 @@ _ALPHA_MONTH_RANGE = (
|
|||||||
+ r")"
|
+ r")"
|
||||||
+ r")\b"
|
+ r")\b"
|
||||||
)
|
)
|
||||||
ALPHA_MONTH_RANGE_RE = re_compile(_ALPHA_MONTH_RANGE)
|
ALPHA_MONTH_RANGE_RE: Pattern = re_compile(_ALPHA_MONTH_RANGE)
|
||||||
|
|
||||||
_DAY_RE_EXP = r"(?P<day>([0-2]?\d|(3)[0-1]))"
|
_DAY_RE_EXP = r"(?P<day>([0-2]?\d|(3)[0-1]))"
|
||||||
_DATE_DELIM = r"[-\s]+"
|
_DATE_DELIM = r"[-\s]+"
|
||||||
@ -144,10 +145,10 @@ _YEAR_FIRST_DATE_RE_EXP = (
|
|||||||
+ r"\b\)?)"
|
+ r"\b\)?)"
|
||||||
)
|
)
|
||||||
|
|
||||||
MONTH_FIRST_DATE_RE = re_compile(_MONTH_FIRST_DATE_RE_EXP)
|
MONTH_FIRST_DATE_RE: Pattern = re_compile(_MONTH_FIRST_DATE_RE_EXP)
|
||||||
YEAR_FIRST_DATE_RE = re_compile(_YEAR_FIRST_DATE_RE_EXP)
|
YEAR_FIRST_DATE_RE: Pattern = re_compile(_YEAR_FIRST_DATE_RE_EXP)
|
||||||
YEAR_TOKEN_RE = re_compile(_YEAR_RE_EXP, parenthify=True)
|
YEAR_TOKEN_RE: Pattern = re_compile(_YEAR_RE_EXP, parenthify=True)
|
||||||
YEAR_END_RE = re_compile(_YEAR_RE_EXP + r"\/|$")
|
YEAR_END_RE: Pattern = re_compile(_YEAR_RE_EXP + r"\/|$")
|
||||||
|
|
||||||
# PAREN GROUPS
|
# PAREN GROUPS
|
||||||
_OF_PATTERNS = r"|".join(ORIGINAL_FORMAT_PATTERNS)
|
_OF_PATTERNS = r"|".join(ORIGINAL_FORMAT_PATTERNS)
|
||||||
@ -156,37 +157,39 @@ _SCAN_INFO_RE_EXP = r"(?P<scan_info>[^()]*)"
|
|||||||
_ORIGINAL_FORMAT_SCAN_INFO_RE_EXP = (
|
_ORIGINAL_FORMAT_SCAN_INFO_RE_EXP = (
|
||||||
_ORIGINAL_FORMAT_RE_EXP + r"\s*[\(:-]" + _SCAN_INFO_RE_EXP # + r")?"
|
_ORIGINAL_FORMAT_RE_EXP + r"\s*[\(:-]" + _SCAN_INFO_RE_EXP # + r")?"
|
||||||
)
|
)
|
||||||
ORIGINAL_FORMAT_SCAN_INFO_RE = re_compile(
|
# Keep this even though comicfn2dict doesn't use it directly
|
||||||
|
ORIGINAL_FORMAT_RE: Pattern = re_compile(_ORIGINAL_FORMAT_RE_EXP, parenthify=True)
|
||||||
|
ORIGINAL_FORMAT_SCAN_INFO_RE: Pattern = re_compile(
|
||||||
_ORIGINAL_FORMAT_SCAN_INFO_RE_EXP, parenthify=True
|
_ORIGINAL_FORMAT_SCAN_INFO_RE_EXP, parenthify=True
|
||||||
)
|
)
|
||||||
ORIGINAL_FORMAT_SCAN_INFO_SEPARATE_RE = re_compile(
|
ORIGINAL_FORMAT_SCAN_INFO_SEPARATE_RE: Pattern = re_compile(
|
||||||
r"\(" + _ORIGINAL_FORMAT_RE_EXP + r"\).*\(" + _SCAN_INFO_RE_EXP + r"\)"
|
r"\(" + _ORIGINAL_FORMAT_RE_EXP + r"\).*\(" + _SCAN_INFO_RE_EXP + r"\)"
|
||||||
)
|
)
|
||||||
|
|
||||||
SCAN_INFO_SECONDARY_RE = re_compile(r"\b(?P<secondary_scan_info>c2c)\b")
|
SCAN_INFO_SECONDARY_RE: Pattern = re_compile(r"\b(?P<secondary_scan_info>c2c)\b")
|
||||||
|
|
||||||
# ISSUE
|
# ISSUE
|
||||||
_ISSUE_RE_EXP = r"(?P<issue>\w*(½|\d+)[\.\d+]*\w*)"
|
_ISSUE_RE_EXP = r"(?P<issue>\w*(½|\d+)[\.\d+]*\w*)"
|
||||||
_ISSUE_COUNT_RE_EXP = r"\(of\s*(?P<issue_count>\d+)\)"
|
_ISSUE_COUNT_RE_EXP = r"\(of\s*(?P<issue_count>\d+)\)"
|
||||||
ISSUE_NUMBER_RE = re_compile(
|
ISSUE_NUMBER_RE: Pattern = re_compile(
|
||||||
r"(\(?#" + _ISSUE_RE_EXP + r"\)?)" + r"(\W*" + _ISSUE_COUNT_RE_EXP + r")?"
|
r"(\(?#" + _ISSUE_RE_EXP + r"\)?)" + r"(\W*" + _ISSUE_COUNT_RE_EXP + r")?"
|
||||||
)
|
)
|
||||||
ISSUE_WITH_COUNT_RE = re_compile(
|
ISSUE_WITH_COUNT_RE: Pattern = re_compile(
|
||||||
r"(\(?" + _ISSUE_RE_EXP + r"\)?" + r"\W*" + _ISSUE_COUNT_RE_EXP + r")"
|
r"(\(?" + _ISSUE_RE_EXP + r"\)?" + r"\W*" + _ISSUE_COUNT_RE_EXP + r")"
|
||||||
)
|
)
|
||||||
ISSUE_END_RE = re_compile(r"([\/\s]\(?" + _ISSUE_RE_EXP + r"\)?(\/|$))")
|
ISSUE_END_RE: Pattern = re_compile(r"([\/\s]\(?" + _ISSUE_RE_EXP + r"\)?(\/|$))")
|
||||||
ISSUE_BEGIN_RE = re_compile(r"((^|\/)\(?" + _ISSUE_RE_EXP + r"\)?[\/|\s])")
|
ISSUE_BEGIN_RE: Pattern = re_compile(r"((^|\/)\(?" + _ISSUE_RE_EXP + r"\)?[\/|\s])")
|
||||||
|
|
||||||
# Volume
|
# Volume
|
||||||
_VOLUME_COUNT_RE_EXP = r"\(of\s*(?P<volume_count>\d+)\)"
|
_VOLUME_COUNT_RE_EXP = r"\(of\s*(?P<volume_count>\d+)\)"
|
||||||
VOLUME_RE = re_compile(
|
VOLUME_RE: Pattern = re_compile(
|
||||||
r"(" + r"(?:v(?:ol(?:ume)?)?\.?)\s*(?P<volume>\d+)"
|
r"(" + r"(?:v(?:ol(?:ume)?)?\.?)\s*(?P<volume>\d+)" # noqa: ISC003
|
||||||
r"(\W*" + _VOLUME_COUNT_RE_EXP + r")?" + r")"
|
r"(\W*" + _VOLUME_COUNT_RE_EXP + r")?" + r")"
|
||||||
)
|
)
|
||||||
VOLUME_WITH_COUNT_RE = re_compile(
|
VOLUME_WITH_COUNT_RE: Pattern = re_compile(
|
||||||
r"(\(?" + r"(?P<volume>\d+)" + r"\)?" + r"\W*" + _VOLUME_COUNT_RE_EXP + r")"
|
r"(\(?" + r"(?P<volume>\d+)" + r"\)?" + r"\W*" + _VOLUME_COUNT_RE_EXP + r")"
|
||||||
)
|
)
|
||||||
BOOK_VOLUME_RE = re_compile(r"(?P<title>" + r"book\s*(?P<volume>\d+)" + r")")
|
BOOK_VOLUME_RE: Pattern = re_compile(r"(?P<title>" + r"book\s*(?P<volume>\d+)" + r")")
|
||||||
|
|
||||||
# Publisher
|
# Publisher
|
||||||
_PUBLISHER_UNAMBIGUOUS_RE_EXP = (
|
_PUBLISHER_UNAMBIGUOUS_RE_EXP = (
|
||||||
@ -195,15 +198,15 @@ _PUBLISHER_UNAMBIGUOUS_RE_EXP = (
|
|||||||
_PUBLISHER_AMBIGUOUS_RE_EXP = (
|
_PUBLISHER_AMBIGUOUS_RE_EXP = (
|
||||||
r"(\b(?P<publisher>" + r"|".join(PUBLISHERS_AMBIGUOUS) + r")\b)"
|
r"(\b(?P<publisher>" + r"|".join(PUBLISHERS_AMBIGUOUS) + r")\b)"
|
||||||
)
|
)
|
||||||
PUBLISHER_UNAMBIGUOUS_TOKEN_RE = re_compile(
|
PUBLISHER_UNAMBIGUOUS_TOKEN_RE: Pattern = re_compile(
|
||||||
r"(^|\/)" + _PUBLISHER_UNAMBIGUOUS_RE_EXP + r"($|\/)"
|
r"(^|\/)" + _PUBLISHER_UNAMBIGUOUS_RE_EXP + r"($|\/)"
|
||||||
)
|
)
|
||||||
PUBLISHER_AMBIGUOUS_TOKEN_RE = re_compile(
|
PUBLISHER_AMBIGUOUS_TOKEN_RE: Pattern = re_compile(
|
||||||
r"(^|\/)" + _PUBLISHER_AMBIGUOUS_RE_EXP + r"($|\/)"
|
r"(^|\/)" + _PUBLISHER_AMBIGUOUS_RE_EXP + r"($|\/)"
|
||||||
)
|
)
|
||||||
PUBLISHER_UNAMBIGUOUS_RE = re_compile(_PUBLISHER_UNAMBIGUOUS_RE_EXP)
|
PUBLISHER_UNAMBIGUOUS_RE: Pattern = re_compile(_PUBLISHER_UNAMBIGUOUS_RE_EXP)
|
||||||
PUBLISHER_AMBIGUOUS_RE = re_compile(_PUBLISHER_AMBIGUOUS_RE_EXP)
|
PUBLISHER_AMBIGUOUS_RE = re_compile(_PUBLISHER_AMBIGUOUS_RE_EXP)
|
||||||
|
|
||||||
# LONG STRINGS
|
# LONG STRINGS
|
||||||
REMAINING_GROUP_RE = re_compile(r"^[^\(].*[^\)]")
|
REMAINING_GROUP_RE: Pattern = re_compile(r"^[^\(].*[^\)]")
|
||||||
NON_NUMBER_DOT_RE = re_compile(r"(\D)\.(\D)")
|
NON_NUMBER_DOT_RE: Pattern = re_compile(r"(\D)\.(\D)")
|
||||||
|
@ -1,8 +1,12 @@
|
|||||||
"""Unparse comic filenames."""
|
"""Unparse comic filenames."""
|
||||||
|
|
||||||
|
from __future__ import annotations
|
||||||
|
|
||||||
|
from calendar import month_abbr
|
||||||
from collections.abc import Callable, Mapping, Sequence
|
from collections.abc import Callable, Mapping, Sequence
|
||||||
from contextlib import suppress
|
from contextlib import suppress
|
||||||
from calendar import month_abbr
|
|
||||||
from types import MappingProxyType
|
from types import MappingProxyType
|
||||||
|
|
||||||
from comicfn2dict.log import print_log_header
|
from comicfn2dict.log import print_log_header
|
||||||
|
|
||||||
|
|
||||||
@ -39,12 +43,12 @@ _DATE_KEYS = ("year", "month", "day")
|
|||||||
class ComicFilenameSerializer:
|
class ComicFilenameSerializer:
|
||||||
"""Serialize Comic Filenames from dict."""
|
"""Serialize Comic Filenames from dict."""
|
||||||
|
|
||||||
def _log(self, label, fn):
|
def _log(self, label: str, fn: str) -> None:
|
||||||
"""Log progress."""
|
"""Log progress."""
|
||||||
if not self._debug:
|
if not self._debug:
|
||||||
return
|
return
|
||||||
print_log_header(label)
|
print_log_header(label)
|
||||||
print(fn)
|
print(fn) # noqa: T201
|
||||||
|
|
||||||
def _add_date(self) -> None:
|
def _add_date(self) -> None:
|
||||||
"""Construct date from Y-m-D if they exist."""
|
"""Construct date from Y-m-D if they exist."""
|
||||||
@ -62,6 +66,7 @@ class ComicFilenameSerializer:
|
|||||||
# noop if only day.
|
# noop if only day.
|
||||||
break
|
break
|
||||||
if parts:
|
if parts:
|
||||||
|
parts = (str(part) for part in parts)
|
||||||
date = "-".join(parts)
|
date = "-".join(parts)
|
||||||
self._log("After date", date)
|
self._log("After date", date)
|
||||||
self.metadata = MappingProxyType({**self.metadata, "date": date})
|
self.metadata = MappingProxyType({**self.metadata, "date": date})
|
||||||
@ -72,13 +77,13 @@ class ComicFilenameSerializer:
|
|||||||
if val in _EMPTY_VALUES:
|
if val in _EMPTY_VALUES:
|
||||||
return ""
|
return ""
|
||||||
final_fmt = fmt(val) if isinstance(fmt, Callable) else fmt
|
final_fmt = fmt(val) if isinstance(fmt, Callable) else fmt
|
||||||
token = final_fmt.format(val).strip()
|
return final_fmt.format(val).strip()
|
||||||
return token
|
|
||||||
|
|
||||||
def _add_remainder(self) -> str:
|
def _add_remainder(self) -> str:
|
||||||
"""Add the remainders specially."""
|
"""Add the remainders specially."""
|
||||||
if remainders := self.metadata.get("remainders"):
|
if remainders := self.metadata.get("remainders"):
|
||||||
if isinstance(remainders, Sequence):
|
if isinstance(remainders, Sequence):
|
||||||
|
remainders = (str(remainder) for remainder in remainders)
|
||||||
remainder = " ".join(remainders)
|
remainder = " ".join(remainders)
|
||||||
else:
|
else:
|
||||||
remainder = str(remainders)
|
remainder = str(remainders)
|
||||||
@ -93,7 +98,7 @@ class ComicFilenameSerializer:
|
|||||||
for tag, fmt in _FILENAME_FORMAT_TAGS:
|
for tag, fmt in _FILENAME_FORMAT_TAGS:
|
||||||
if token := self._tokenize_tag(tag, fmt):
|
if token := self._tokenize_tag(tag, fmt):
|
||||||
tokens.append(token)
|
tokens.append(token)
|
||||||
self._log(f"After {tag}", tokens)
|
self._log(f"After {tag}", str(tokens))
|
||||||
fn = " ".join(tokens)
|
fn = " ".join(tokens)
|
||||||
|
|
||||||
fn += self._add_remainder()
|
fn += self._add_remainder()
|
||||||
@ -107,12 +112,13 @@ class ComicFilenameSerializer:
|
|||||||
return fn
|
return fn
|
||||||
|
|
||||||
def __init__(self, metadata: Mapping, ext: bool = True, verbose: int = 0):
|
def __init__(self, metadata: Mapping, ext: bool = True, verbose: int = 0):
|
||||||
|
"""Initialize."""
|
||||||
self.metadata: Mapping = metadata
|
self.metadata: Mapping = metadata
|
||||||
self._ext: bool = ext
|
self._ext: bool = ext
|
||||||
self._debug: bool = bool(verbose)
|
self._debug: bool = bool(verbose)
|
||||||
|
|
||||||
|
|
||||||
def dict2comicfn(md: Mapping, ext: bool = True, verbose: int = 0) -> str:
|
def dict2comicfn(md: Mapping, ext: bool = True, verbose: int = 0) -> str:
|
||||||
"""Simple API."""
|
"""Simplify API."""
|
||||||
serializer = ComicFilenameSerializer(md, ext=ext, verbose=verbose)
|
serializer = ComicFilenameSerializer(md, ext=ext, verbose=verbose)
|
||||||
return serializer.serialize()
|
return serializer.serialize()
|
||||||
|
131
package-lock.json
generated
131
package-lock.json
generated
@ -303,9 +303,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/@babel/parser": {
|
"node_modules/@babel/parser": {
|
||||||
"version": "7.23.9",
|
"version": "7.24.0",
|
||||||
"resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.23.9.tgz",
|
"resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.24.0.tgz",
|
||||||
"integrity": "sha512-9tcKgqKbs3xGJ+NtKF2ndOBBLVwPjl1SHxPQkd36r3Dlirw3xWUeGaTbqr7uGZcTaxkVNwc+03SVP7aCdWrTlA==",
|
"integrity": "sha512-QuP/FxEAzMSjXygs8v4N9dvdXzEHN4W1oF3PxuWAtPo08UdM17u89RDMgjLn/mlc56iM0HlLmVkO/wgR+rDgHg==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"bin": {
|
"bin": {
|
||||||
"parser": "bin/babel-parser.js"
|
"parser": "bin/babel-parser.js"
|
||||||
@ -315,23 +315,23 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/@babel/template": {
|
"node_modules/@babel/template": {
|
||||||
"version": "7.23.9",
|
"version": "7.24.0",
|
||||||
"resolved": "https://registry.npmjs.org/@babel/template/-/template-7.23.9.tgz",
|
"resolved": "https://registry.npmjs.org/@babel/template/-/template-7.24.0.tgz",
|
||||||
"integrity": "sha512-+xrD2BWLpvHKNmX2QbpdpsBaWnRxahMwJjO+KZk2JOElj5nSmKezyS1B4u+QbHMTX69t4ukm6hh9lsYQ7GHCKA==",
|
"integrity": "sha512-Bkf2q8lMB0AFpX0NFEqSbx1OkTHf0f+0j82mkw+ZpzBnkk7e9Ql0891vlfgi+kHwOk8tQjiQHpqh4LaSa0fKEA==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@babel/code-frame": "^7.23.5",
|
"@babel/code-frame": "^7.23.5",
|
||||||
"@babel/parser": "^7.23.9",
|
"@babel/parser": "^7.24.0",
|
||||||
"@babel/types": "^7.23.9"
|
"@babel/types": "^7.24.0"
|
||||||
},
|
},
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">=6.9.0"
|
"node": ">=6.9.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/@babel/traverse": {
|
"node_modules/@babel/traverse": {
|
||||||
"version": "7.23.9",
|
"version": "7.24.0",
|
||||||
"resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.23.9.tgz",
|
"resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.24.0.tgz",
|
||||||
"integrity": "sha512-I/4UJ9vs90OkBtY6iiiTORVMyIhJ4kAVmsKo9KFc8UOxMeUfi2hvtIBsET5u9GizXE6/GFSuKCTNfgCswuEjRg==",
|
"integrity": "sha512-HfuJlI8qq3dEDmNU5ChzzpZRWq+oxCZQyMzIMEqLho+AQnhMnKQUzH6ydo3RBl/YjPCuk68Y6s0Gx0AeyULiWw==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@babel/code-frame": "^7.23.5",
|
"@babel/code-frame": "^7.23.5",
|
||||||
@ -340,8 +340,8 @@
|
|||||||
"@babel/helper-function-name": "^7.23.0",
|
"@babel/helper-function-name": "^7.23.0",
|
||||||
"@babel/helper-hoist-variables": "^7.22.5",
|
"@babel/helper-hoist-variables": "^7.22.5",
|
||||||
"@babel/helper-split-export-declaration": "^7.22.6",
|
"@babel/helper-split-export-declaration": "^7.22.6",
|
||||||
"@babel/parser": "^7.23.9",
|
"@babel/parser": "^7.24.0",
|
||||||
"@babel/types": "^7.23.9",
|
"@babel/types": "^7.24.0",
|
||||||
"debug": "^4.3.1",
|
"debug": "^4.3.1",
|
||||||
"globals": "^11.1.0"
|
"globals": "^11.1.0"
|
||||||
},
|
},
|
||||||
@ -359,9 +359,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/@babel/types": {
|
"node_modules/@babel/types": {
|
||||||
"version": "7.23.9",
|
"version": "7.24.0",
|
||||||
"resolved": "https://registry.npmjs.org/@babel/types/-/types-7.23.9.tgz",
|
"resolved": "https://registry.npmjs.org/@babel/types/-/types-7.24.0.tgz",
|
||||||
"integrity": "sha512-dQjSq/7HaSjRM43FFGnv5keM2HsxpmyV1PfaSVm0nzzjwwTmjOe6J4bC8e3+pTEIgHaHj+1ZlLThRJ2auc/w1Q==",
|
"integrity": "sha512-+j7a5c253RfKh8iABBhywc8NSfP5LURe7Uh4qpsh6jc+aLJguvmIUBdjSdEMQv2bENrCR5MfRdjGo7vzS/ob7w==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@babel/helper-string-parser": "^7.23.4",
|
"@babel/helper-string-parser": "^7.23.4",
|
||||||
@ -590,14 +590,14 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/@jridgewell/gen-mapping": {
|
"node_modules/@jridgewell/gen-mapping": {
|
||||||
"version": "0.3.3",
|
"version": "0.3.5",
|
||||||
"resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.3.tgz",
|
"resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.5.tgz",
|
||||||
"integrity": "sha512-HLhSWOLRi875zjjMG/r+Nv0oCW8umGb0BgEhyX3dDX3egwZtB8PqLnjz3yedt8R5StBrzcg4aBpnh8UA9D1BoQ==",
|
"integrity": "sha512-IzL8ZoEDIBRWEzlCcRhOaCupYyN5gdIK+Q6fbFdPDg6HqX6jpkItn7DFIpW9LQzXG6Df9sA7+OKnq0qlz/GaQg==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@jridgewell/set-array": "^1.0.1",
|
"@jridgewell/set-array": "^1.2.1",
|
||||||
"@jridgewell/sourcemap-codec": "^1.4.10",
|
"@jridgewell/sourcemap-codec": "^1.4.10",
|
||||||
"@jridgewell/trace-mapping": "^0.3.9"
|
"@jridgewell/trace-mapping": "^0.3.24"
|
||||||
},
|
},
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">=6.0.0"
|
"node": ">=6.0.0"
|
||||||
@ -613,9 +613,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/@jridgewell/set-array": {
|
"node_modules/@jridgewell/set-array": {
|
||||||
"version": "1.1.2",
|
"version": "1.2.1",
|
||||||
"resolved": "https://registry.npmjs.org/@jridgewell/set-array/-/set-array-1.1.2.tgz",
|
"resolved": "https://registry.npmjs.org/@jridgewell/set-array/-/set-array-1.2.1.tgz",
|
||||||
"integrity": "sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==",
|
"integrity": "sha512-R8gLRTZeyp03ymzP/6Lil/28tGeGEzhx1q2k703KGWRAI1VdvPIXdG70VJc2pAMw3NA6JKL5hhFu1sJX0Mnn/A==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">=6.0.0"
|
"node": ">=6.0.0"
|
||||||
@ -628,9 +628,9 @@
|
|||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"node_modules/@jridgewell/trace-mapping": {
|
"node_modules/@jridgewell/trace-mapping": {
|
||||||
"version": "0.3.22",
|
"version": "0.3.25",
|
||||||
"resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.22.tgz",
|
"resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.25.tgz",
|
||||||
"integrity": "sha512-Wf963MzWtA2sjrNt+g18IAln9lKnlRp+K2eH4jjIoF1wYeq3aMREpG09xhlhdzS0EjwU7qmUJYangWa+151vZw==",
|
"integrity": "sha512-vNk6aEwybGtawWmy/PzwnGDOjCkLWSD2wqvjGGAgOAwCGWySYXfYoxt00IJkTF+8Lb57DwOb3Aa0o9CApepiYQ==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@jridgewell/resolve-uri": "^3.1.0",
|
"@jridgewell/resolve-uri": "^3.1.0",
|
||||||
@ -673,9 +673,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/@npmcli/config": {
|
"node_modules/@npmcli/config": {
|
||||||
"version": "8.1.0",
|
"version": "8.2.0",
|
||||||
"resolved": "https://registry.npmjs.org/@npmcli/config/-/config-8.1.0.tgz",
|
"resolved": "https://registry.npmjs.org/@npmcli/config/-/config-8.2.0.tgz",
|
||||||
"integrity": "sha512-61LNEybTFaa9Z/f8y6X9s2Blc75aijZK67LxqC5xicBcfkw8M/88nYrRXGXxAUKm6GRlxTZ216dp1UK2+TbaYw==",
|
"integrity": "sha512-YoEYZFg0hRSRP/Chmq+J4FvULFvji6SORUYWQc10FiJ+ReAnViXcDCENg6kM6dID04bAoKNUygrby798+gYBbQ==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@npmcli/map-workspaces": "^3.0.2",
|
"@npmcli/map-workspaces": "^3.0.2",
|
||||||
@ -856,9 +856,9 @@
|
|||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"node_modules/@types/node": {
|
"node_modules/@types/node": {
|
||||||
"version": "20.11.20",
|
"version": "20.11.24",
|
||||||
"resolved": "https://registry.npmjs.org/@types/node/-/node-20.11.20.tgz",
|
"resolved": "https://registry.npmjs.org/@types/node/-/node-20.11.24.tgz",
|
||||||
"integrity": "sha512-7/rR21OS+fq8IyHTgtLkDK949uzsa6n8BkziAKtPVpugIkO6D+/ooXMvzXxDnZrmtXVfjb1bKQafYpb8s89LOg==",
|
"integrity": "sha512-Kza43ewS3xoLgCEpQrsT+xRo/EJej1y0kVYGiLFE1NEODXGzTfwiC6tXTLMQskn1X4/Rjlh0MQUvx9W+L9long==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"undici-types": "~5.26.4"
|
"undici-types": "~5.26.4"
|
||||||
@ -1364,9 +1364,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/caniuse-lite": {
|
"node_modules/caniuse-lite": {
|
||||||
"version": "1.0.30001589",
|
"version": "1.0.30001593",
|
||||||
"resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001589.tgz",
|
"resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001593.tgz",
|
||||||
"integrity": "sha512-vNQWS6kI+q6sBlHbh71IIeC+sRwK2N3EDySc/updIGhIee2x5z00J4c1242/5/d6EpEMdOnk/m+6tuk4/tcsqg==",
|
"integrity": "sha512-UWM1zlo3cZfkpBysd7AS+z+v007q9G1+fLTUU42rQnY6t2axoogPW/xol6T7juU5EUoOhML4WgBIdG+9yYqAjQ==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"funding": [
|
"funding": [
|
||||||
{
|
{
|
||||||
@ -1780,9 +1780,9 @@
|
|||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"node_modules/electron-to-chromium": {
|
"node_modules/electron-to-chromium": {
|
||||||
"version": "1.4.681",
|
"version": "1.4.691",
|
||||||
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.681.tgz",
|
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.691.tgz",
|
||||||
"integrity": "sha512-1PpuqJUFWoXZ1E54m8bsLPVYwIVCRzvaL+n5cjigGga4z854abDnFRc+cTa2th4S79kyGqya/1xoR7h+Y5G5lg==",
|
"integrity": "sha512-vJ+/LmKja/St8Ofq4JGMFVZuwG7ECU6akjNSn2/g6nv8xbIBOWGlEs+WA8/3XaWkU0Nlyu0iFGgOxC4mpgFjgA==",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"node_modules/emoji-regex": {
|
"node_modules/emoji-regex": {
|
||||||
@ -1801,18 +1801,18 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/es-abstract": {
|
"node_modules/es-abstract": {
|
||||||
"version": "1.22.4",
|
"version": "1.22.5",
|
||||||
"resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.22.4.tgz",
|
"resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.22.5.tgz",
|
||||||
"integrity": "sha512-vZYJlk2u6qHYxBOTjAeg7qUxHdNfih64Uu2J8QqWgXZ2cri0ZpJAkzDUK/q593+mvKwlxyaxr6F1Q+3LKoQRgg==",
|
"integrity": "sha512-oW69R+4q2wG+Hc3KZePPZxOiisRIqfKBVo/HLx94QcJeWGU/8sZhCvc829rd1kS366vlJbzBfXf9yWwf0+Ko7w==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"array-buffer-byte-length": "^1.0.1",
|
"array-buffer-byte-length": "^1.0.1",
|
||||||
"arraybuffer.prototype.slice": "^1.0.3",
|
"arraybuffer.prototype.slice": "^1.0.3",
|
||||||
"available-typed-arrays": "^1.0.6",
|
"available-typed-arrays": "^1.0.7",
|
||||||
"call-bind": "^1.0.7",
|
"call-bind": "^1.0.7",
|
||||||
"es-define-property": "^1.0.0",
|
"es-define-property": "^1.0.0",
|
||||||
"es-errors": "^1.3.0",
|
"es-errors": "^1.3.0",
|
||||||
"es-set-tostringtag": "^2.0.2",
|
"es-set-tostringtag": "^2.0.3",
|
||||||
"es-to-primitive": "^1.2.1",
|
"es-to-primitive": "^1.2.1",
|
||||||
"function.prototype.name": "^1.1.6",
|
"function.prototype.name": "^1.1.6",
|
||||||
"get-intrinsic": "^1.2.4",
|
"get-intrinsic": "^1.2.4",
|
||||||
@ -1820,15 +1820,15 @@
|
|||||||
"globalthis": "^1.0.3",
|
"globalthis": "^1.0.3",
|
||||||
"gopd": "^1.0.1",
|
"gopd": "^1.0.1",
|
||||||
"has-property-descriptors": "^1.0.2",
|
"has-property-descriptors": "^1.0.2",
|
||||||
"has-proto": "^1.0.1",
|
"has-proto": "^1.0.3",
|
||||||
"has-symbols": "^1.0.3",
|
"has-symbols": "^1.0.3",
|
||||||
"hasown": "^2.0.1",
|
"hasown": "^2.0.1",
|
||||||
"internal-slot": "^1.0.7",
|
"internal-slot": "^1.0.7",
|
||||||
"is-array-buffer": "^3.0.4",
|
"is-array-buffer": "^3.0.4",
|
||||||
"is-callable": "^1.2.7",
|
"is-callable": "^1.2.7",
|
||||||
"is-negative-zero": "^2.0.2",
|
"is-negative-zero": "^2.0.3",
|
||||||
"is-regex": "^1.1.4",
|
"is-regex": "^1.1.4",
|
||||||
"is-shared-array-buffer": "^1.0.2",
|
"is-shared-array-buffer": "^1.0.3",
|
||||||
"is-string": "^1.0.7",
|
"is-string": "^1.0.7",
|
||||||
"is-typed-array": "^1.1.13",
|
"is-typed-array": "^1.1.13",
|
||||||
"is-weakref": "^1.0.2",
|
"is-weakref": "^1.0.2",
|
||||||
@ -1841,10 +1841,10 @@
|
|||||||
"string.prototype.trim": "^1.2.8",
|
"string.prototype.trim": "^1.2.8",
|
||||||
"string.prototype.trimend": "^1.0.7",
|
"string.prototype.trimend": "^1.0.7",
|
||||||
"string.prototype.trimstart": "^1.0.7",
|
"string.prototype.trimstart": "^1.0.7",
|
||||||
"typed-array-buffer": "^1.0.1",
|
"typed-array-buffer": "^1.0.2",
|
||||||
"typed-array-byte-length": "^1.0.0",
|
"typed-array-byte-length": "^1.0.1",
|
||||||
"typed-array-byte-offset": "^1.0.0",
|
"typed-array-byte-offset": "^1.0.2",
|
||||||
"typed-array-length": "^1.0.4",
|
"typed-array-length": "^1.0.5",
|
||||||
"unbox-primitive": "^1.0.2",
|
"unbox-primitive": "^1.0.2",
|
||||||
"which-typed-array": "^1.1.14"
|
"which-typed-array": "^1.1.14"
|
||||||
},
|
},
|
||||||
@ -2061,9 +2061,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/eslint-module-utils": {
|
"node_modules/eslint-module-utils": {
|
||||||
"version": "2.8.0",
|
"version": "2.8.1",
|
||||||
"resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.8.0.tgz",
|
"resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.8.1.tgz",
|
||||||
"integrity": "sha512-aWajIYfsqCKRDgUfjEXNN/JlrzauMuSEy5sbd7WXbtW3EH6A6MpwEh42c7qD+MqQo9QMJ6fWLAeIJynx0g6OAw==",
|
"integrity": "sha512-rXDXR3h7cs7dy9RNpUlQf80nX31XWJEyGq1tRMo+6GsO5VmTe4UTwtmonAD4ZkAsrfMVDA2wlGJ3790Ys+D49Q==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"debug": "^3.2.7"
|
"debug": "^3.2.7"
|
||||||
@ -3171,9 +3171,9 @@
|
|||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"node_modules/ini": {
|
"node_modules/ini": {
|
||||||
"version": "4.1.1",
|
"version": "4.1.2",
|
||||||
"resolved": "https://registry.npmjs.org/ini/-/ini-4.1.1.tgz",
|
"resolved": "https://registry.npmjs.org/ini/-/ini-4.1.2.tgz",
|
||||||
"integrity": "sha512-QQnnxNyfvmHFIsj7gkPcYymR8Jdw/o7mp5ZFihxn6h8Ci6fh3Dx4E1gPjpQEpIuPo9XVNY/ZUwh4BPMjGyL01g==",
|
"integrity": "sha512-AMB1mvwR1pyBFY/nSevUX6y8nJWS63/SzUKD3JyQn97s4xgIdgQPT75IRouIiBAN4yLQBUShNYVW0+UG25daCw==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": "^14.17.0 || ^16.13.0 || >=18.0.0"
|
"node": "^14.17.0 || ^16.13.0 || >=18.0.0"
|
||||||
@ -11088,12 +11088,12 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/side-channel": {
|
"node_modules/side-channel": {
|
||||||
"version": "1.0.5",
|
"version": "1.0.6",
|
||||||
"resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.5.tgz",
|
"resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.6.tgz",
|
||||||
"integrity": "sha512-QcgiIWV4WV7qWExbN5llt6frQB/lBven9pqliLXfGPB+K9ZYXxDozp0wLkHS24kWCm+6YXH/f0HhnObZnZOBnQ==",
|
"integrity": "sha512-fDW/EZ6Q9RiO8eFG8Hj+7u/oW+XrPTIChwCOM2+th2A6OblDtYYIpve9m+KvI9Z4C9qSEXlaGR6bTEYHReuglA==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"call-bind": "^1.0.6",
|
"call-bind": "^1.0.7",
|
||||||
"es-errors": "^1.3.0",
|
"es-errors": "^1.3.0",
|
||||||
"get-intrinsic": "^1.2.4",
|
"get-intrinsic": "^1.2.4",
|
||||||
"object-inspect": "^1.13.1"
|
"object-inspect": "^1.13.1"
|
||||||
@ -12663,10 +12663,13 @@
|
|||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"node_modules/yaml": {
|
"node_modules/yaml": {
|
||||||
"version": "2.3.4",
|
"version": "2.4.0",
|
||||||
"resolved": "https://registry.npmjs.org/yaml/-/yaml-2.3.4.tgz",
|
"resolved": "https://registry.npmjs.org/yaml/-/yaml-2.4.0.tgz",
|
||||||
"integrity": "sha512-8aAvwVUSHpfEqTQ4w/KMlf3HcRdt50E5ODIQJBw1fQ5RL34xabzxtUlzTXVqc4rkZsPbvrXKWnABCD7kWSmocA==",
|
"integrity": "sha512-j9iR8g+/t0lArF4V6NE/QCfT+CO7iLqrXAHZbJdo+LfjqP1vR8Fg5bSiaq6Q2lOD1AUEVrEVIgABvBFYojJVYQ==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
|
"bin": {
|
||||||
|
"yaml": "bin.mjs"
|
||||||
|
},
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">= 14"
|
"node": ">= 14"
|
||||||
}
|
}
|
||||||
|
174
poetry.lock
generated
174
poetry.lock
generated
@ -1,4 +1,4 @@
|
|||||||
# This file is automatically @generated by Poetry 1.7.1 and should not be changed by hand.
|
# This file is automatically @generated by Poetry 1.8.2 and should not be changed by hand.
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "click"
|
name = "click"
|
||||||
@ -328,13 +328,13 @@ six = ">=1.13.0"
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "json5"
|
name = "json5"
|
||||||
version = "0.9.17"
|
version = "0.9.20"
|
||||||
description = "A Python implementation of the JSON5 data format."
|
description = "A Python implementation of the JSON5 data format."
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.8"
|
python-versions = ">=3.8"
|
||||||
files = [
|
files = [
|
||||||
{ file = "json5-0.9.17-py2.py3-none-any.whl", hash = "sha256:f8ec1ecf985951d70f780f6f877c4baca6a47b6e61e02c4cd190138d10a7805a" },
|
{ file = "json5-0.9.20-py3-none-any.whl", hash = "sha256:f623485b37fad95783233bad9352d21526709cbd9a2ec41ddc3e950fca85b701" },
|
||||||
{ file = "json5-0.9.17.tar.gz", hash = "sha256:717d99d657fa71b7094877b1d921b1cce40ab444389f6d770302563bb7dfd9ae" },
|
{ file = "json5-0.9.20.tar.gz", hash = "sha256:20a255981244081d5aaa4adc90d31cdbf05bed1863993cbf300b8e2cd2b6de88" },
|
||||||
]
|
]
|
||||||
|
|
||||||
[package.extras]
|
[package.extras]
|
||||||
@ -359,67 +359,67 @@ restructuredtext = ["rst2ansi"]
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "msgpack"
|
name = "msgpack"
|
||||||
version = "1.0.7"
|
version = "1.0.8"
|
||||||
description = "MessagePack serializer"
|
description = "MessagePack serializer"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.8"
|
python-versions = ">=3.8"
|
||||||
files = [
|
files = [
|
||||||
{ file = "msgpack-1.0.7-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:04ad6069c86e531682f9e1e71b71c1c3937d6014a7c3e9edd2aa81ad58842862" },
|
{ file = "msgpack-1.0.8-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:505fe3d03856ac7d215dbe005414bc28505d26f0c128906037e66d98c4e95868" },
|
||||||
{ file = "msgpack-1.0.7-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:cca1b62fe70d761a282496b96a5e51c44c213e410a964bdffe0928e611368329" },
|
{ file = "msgpack-1.0.8-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:e6b7842518a63a9f17107eb176320960ec095a8ee3b4420b5f688e24bf50c53c" },
|
||||||
{ file = "msgpack-1.0.7-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:e50ebce52f41370707f1e21a59514e3375e3edd6e1832f5e5235237db933c98b" },
|
{ file = "msgpack-1.0.8-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:376081f471a2ef24828b83a641a02c575d6103a3ad7fd7dade5486cad10ea659" },
|
||||||
{ file = "msgpack-1.0.7-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:4a7b4f35de6a304b5533c238bee86b670b75b03d31b7797929caa7a624b5dda6" },
|
{ file = "msgpack-1.0.8-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5e390971d082dba073c05dbd56322427d3280b7cc8b53484c9377adfbae67dc2" },
|
||||||
{ file = "msgpack-1.0.7-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:28efb066cde83c479dfe5a48141a53bc7e5f13f785b92ddde336c716663039ee" },
|
{ file = "msgpack-1.0.8-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:00e073efcba9ea99db5acef3959efa45b52bc67b61b00823d2a1a6944bf45982" },
|
||||||
{ file = "msgpack-1.0.7-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:4cb14ce54d9b857be9591ac364cb08dc2d6a5c4318c1182cb1d02274029d590d" },
|
{ file = "msgpack-1.0.8-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:82d92c773fbc6942a7a8b520d22c11cfc8fd83bba86116bfcf962c2f5c2ecdaa" },
|
||||||
{ file = "msgpack-1.0.7-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:b573a43ef7c368ba4ea06050a957c2a7550f729c31f11dd616d2ac4aba99888d" },
|
{ file = "msgpack-1.0.8-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:9ee32dcb8e531adae1f1ca568822e9b3a738369b3b686d1477cbc643c4a9c128" },
|
||||||
{ file = "msgpack-1.0.7-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:ccf9a39706b604d884d2cb1e27fe973bc55f2890c52f38df742bc1d79ab9f5e1" },
|
{ file = "msgpack-1.0.8-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:e3aa7e51d738e0ec0afbed661261513b38b3014754c9459508399baf14ae0c9d" },
|
||||||
{ file = "msgpack-1.0.7-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:cb70766519500281815dfd7a87d3a178acf7ce95390544b8c90587d76b227681" },
|
{ file = "msgpack-1.0.8-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:69284049d07fce531c17404fcba2bb1df472bc2dcdac642ae71a2d079d950653" },
|
||||||
{ file = "msgpack-1.0.7-cp310-cp310-win32.whl", hash = "sha256:b610ff0f24e9f11c9ae653c67ff8cc03c075131401b3e5ef4b82570d1728f8a9" },
|
{ file = "msgpack-1.0.8-cp310-cp310-win32.whl", hash = "sha256:13577ec9e247f8741c84d06b9ece5f654920d8365a4b636ce0e44f15e07ec693" },
|
||||||
{ file = "msgpack-1.0.7-cp310-cp310-win_amd64.whl", hash = "sha256:a40821a89dc373d6427e2b44b572efc36a2778d3f543299e2f24eb1a5de65415" },
|
{ file = "msgpack-1.0.8-cp310-cp310-win_amd64.whl", hash = "sha256:e532dbd6ddfe13946de050d7474e3f5fb6ec774fbb1a188aaf469b08cf04189a" },
|
||||||
{ file = "msgpack-1.0.7-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:576eb384292b139821c41995523654ad82d1916da6a60cff129c715a6223ea84" },
|
{ file = "msgpack-1.0.8-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:9517004e21664f2b5a5fd6333b0731b9cf0817403a941b393d89a2f1dc2bd836" },
|
||||||
{ file = "msgpack-1.0.7-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:730076207cb816138cf1af7f7237b208340a2c5e749707457d70705715c93b93" },
|
{ file = "msgpack-1.0.8-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:d16a786905034e7e34098634b184a7d81f91d4c3d246edc6bd7aefb2fd8ea6ad" },
|
||||||
{ file = "msgpack-1.0.7-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:85765fdf4b27eb5086f05ac0491090fc76f4f2b28e09d9350c31aac25a5aaff8" },
|
{ file = "msgpack-1.0.8-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:e2872993e209f7ed04d963e4b4fbae72d034844ec66bc4ca403329db2074377b" },
|
||||||
{ file = "msgpack-1.0.7-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3476fae43db72bd11f29a5147ae2f3cb22e2f1a91d575ef130d2bf49afd21c46" },
|
{ file = "msgpack-1.0.8-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5c330eace3dd100bdb54b5653b966de7f51c26ec4a7d4e87132d9b4f738220ba" },
|
||||||
{ file = "msgpack-1.0.7-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6d4c80667de2e36970ebf74f42d1088cc9ee7ef5f4e8c35eee1b40eafd33ca5b" },
|
{ file = "msgpack-1.0.8-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:83b5c044f3eff2a6534768ccfd50425939e7a8b5cf9a7261c385de1e20dcfc85" },
|
||||||
{ file = "msgpack-1.0.7-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:5b0bf0effb196ed76b7ad883848143427a73c355ae8e569fa538365064188b8e" },
|
{ file = "msgpack-1.0.8-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:1876b0b653a808fcd50123b953af170c535027bf1d053b59790eebb0aeb38950" },
|
||||||
{ file = "msgpack-1.0.7-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:f9a7c509542db4eceed3dcf21ee5267ab565a83555c9b88a8109dcecc4709002" },
|
{ file = "msgpack-1.0.8-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:dfe1f0f0ed5785c187144c46a292b8c34c1295c01da12e10ccddfc16def4448a" },
|
||||||
{ file = "msgpack-1.0.7-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:84b0daf226913133f899ea9b30618722d45feffa67e4fe867b0b5ae83a34060c" },
|
{ file = "msgpack-1.0.8-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:3528807cbbb7f315bb81959d5961855e7ba52aa60a3097151cb21956fbc7502b" },
|
||||||
{ file = "msgpack-1.0.7-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:ec79ff6159dffcc30853b2ad612ed572af86c92b5168aa3fc01a67b0fa40665e" },
|
{ file = "msgpack-1.0.8-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:e2f879ab92ce502a1e65fce390eab619774dda6a6ff719718069ac94084098ce" },
|
||||||
{ file = "msgpack-1.0.7-cp311-cp311-win32.whl", hash = "sha256:3e7bf4442b310ff154b7bb9d81eb2c016b7d597e364f97d72b1acc3817a0fdc1" },
|
{ file = "msgpack-1.0.8-cp311-cp311-win32.whl", hash = "sha256:26ee97a8261e6e35885c2ecd2fd4a6d38252246f94a2aec23665a4e66d066305" },
|
||||||
{ file = "msgpack-1.0.7-cp311-cp311-win_amd64.whl", hash = "sha256:3f0c8c6dfa6605ab8ff0611995ee30d4f9fcff89966cf562733b4008a3d60d82" },
|
{ file = "msgpack-1.0.8-cp311-cp311-win_amd64.whl", hash = "sha256:eadb9f826c138e6cf3c49d6f8de88225a3c0ab181a9b4ba792e006e5292d150e" },
|
||||||
{ file = "msgpack-1.0.7-cp312-cp312-macosx_10_9_universal2.whl", hash = "sha256:f0936e08e0003f66bfd97e74ee530427707297b0d0361247e9b4f59ab78ddc8b" },
|
{ file = "msgpack-1.0.8-cp312-cp312-macosx_10_9_universal2.whl", hash = "sha256:114be227f5213ef8b215c22dde19532f5da9652e56e8ce969bf0a26d7c419fee" },
|
||||||
{ file = "msgpack-1.0.7-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:98bbd754a422a0b123c66a4c341de0474cad4a5c10c164ceed6ea090f3563db4" },
|
{ file = "msgpack-1.0.8-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:d661dc4785affa9d0edfdd1e59ec056a58b3dbb9f196fa43587f3ddac654ac7b" },
|
||||||
{ file = "msgpack-1.0.7-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:b291f0ee7961a597cbbcc77709374087fa2a9afe7bdb6a40dbbd9b127e79afee" },
|
{ file = "msgpack-1.0.8-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:d56fd9f1f1cdc8227d7b7918f55091349741904d9520c65f0139a9755952c9e8" },
|
||||||
{ file = "msgpack-1.0.7-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ebbbba226f0a108a7366bf4b59bf0f30a12fd5e75100c630267d94d7f0ad20e5" },
|
{ file = "msgpack-1.0.8-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:0726c282d188e204281ebd8de31724b7d749adebc086873a59efb8cf7ae27df3" },
|
||||||
{ file = "msgpack-1.0.7-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:1e2d69948e4132813b8d1131f29f9101bc2c915f26089a6d632001a5c1349672" },
|
{ file = "msgpack-1.0.8-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8db8e423192303ed77cff4dce3a4b88dbfaf43979d280181558af5e2c3c71afc" },
|
||||||
{ file = "msgpack-1.0.7-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:bdf38ba2d393c7911ae989c3bbba510ebbcdf4ecbdbfec36272abe350c454075" },
|
{ file = "msgpack-1.0.8-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:99881222f4a8c2f641f25703963a5cefb076adffd959e0558dc9f803a52d6a58" },
|
||||||
{ file = "msgpack-1.0.7-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:993584fc821c58d5993521bfdcd31a4adf025c7d745bbd4d12ccfecf695af5ba" },
|
{ file = "msgpack-1.0.8-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:b5505774ea2a73a86ea176e8a9a4a7c8bf5d521050f0f6f8426afe798689243f" },
|
||||||
{ file = "msgpack-1.0.7-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:52700dc63a4676669b341ba33520f4d6e43d3ca58d422e22ba66d1736b0a6e4c" },
|
{ file = "msgpack-1.0.8-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:ef254a06bcea461e65ff0373d8a0dd1ed3aa004af48839f002a0c994a6f72d04" },
|
||||||
{ file = "msgpack-1.0.7-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:e45ae4927759289c30ccba8d9fdce62bb414977ba158286b5ddaf8df2cddb5c5" },
|
{ file = "msgpack-1.0.8-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:e1dd7839443592d00e96db831eddb4111a2a81a46b028f0facd60a09ebbdd543" },
|
||||||
{ file = "msgpack-1.0.7-cp312-cp312-win32.whl", hash = "sha256:27dcd6f46a21c18fa5e5deed92a43d4554e3df8d8ca5a47bf0615d6a5f39dbc9" },
|
{ file = "msgpack-1.0.8-cp312-cp312-win32.whl", hash = "sha256:64d0fcd436c5683fdd7c907eeae5e2cbb5eb872fafbc03a43609d7941840995c" },
|
||||||
{ file = "msgpack-1.0.7-cp312-cp312-win_amd64.whl", hash = "sha256:7687e22a31e976a0e7fc99c2f4d11ca45eff652a81eb8c8085e9609298916dcf" },
|
{ file = "msgpack-1.0.8-cp312-cp312-win_amd64.whl", hash = "sha256:74398a4cf19de42e1498368c36eed45d9528f5fd0155241e82c4082b7e16cffd" },
|
||||||
{ file = "msgpack-1.0.7-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:5b6ccc0c85916998d788b295765ea0e9cb9aac7e4a8ed71d12e7d8ac31c23c95" },
|
{ file = "msgpack-1.0.8-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:0ceea77719d45c839fd73abcb190b8390412a890df2f83fb8cf49b2a4b5c2f40" },
|
||||||
{ file = "msgpack-1.0.7-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:235a31ec7db685f5c82233bddf9858748b89b8119bf4538d514536c485c15fe0" },
|
{ file = "msgpack-1.0.8-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:1ab0bbcd4d1f7b6991ee7c753655b481c50084294218de69365f8f1970d4c151" },
|
||||||
{ file = "msgpack-1.0.7-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:cab3db8bab4b7e635c1c97270d7a4b2a90c070b33cbc00c99ef3f9be03d3e1f7" },
|
{ file = "msgpack-1.0.8-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:1cce488457370ffd1f953846f82323cb6b2ad2190987cd4d70b2713e17268d24" },
|
||||||
{ file = "msgpack-1.0.7-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:0bfdd914e55e0d2c9e1526de210f6fe8ffe9705f2b1dfcc4aecc92a4cb4b533d" },
|
{ file = "msgpack-1.0.8-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3923a1778f7e5ef31865893fdca12a8d7dc03a44b33e2a5f3295416314c09f5d" },
|
||||||
{ file = "msgpack-1.0.7-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:36e17c4592231a7dbd2ed09027823ab295d2791b3b1efb2aee874b10548b7524" },
|
{ file = "msgpack-1.0.8-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a22e47578b30a3e199ab067a4d43d790249b3c0587d9a771921f86250c8435db" },
|
||||||
{ file = "msgpack-1.0.7-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:38949d30b11ae5f95c3c91917ee7a6b239f5ec276f271f28638dec9156f82cfc" },
|
{ file = "msgpack-1.0.8-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:bd739c9251d01e0279ce729e37b39d49a08c0420d3fee7f2a4968c0576678f77" },
|
||||||
{ file = "msgpack-1.0.7-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:ff1d0899f104f3921d94579a5638847f783c9b04f2d5f229392ca77fba5b82fc" },
|
{ file = "msgpack-1.0.8-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:d3420522057ebab1728b21ad473aa950026d07cb09da41103f8e597dfbfaeb13" },
|
||||||
{ file = "msgpack-1.0.7-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:dc43f1ec66eb8440567186ae2f8c447d91e0372d793dfe8c222aec857b81a8cf" },
|
{ file = "msgpack-1.0.8-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:5845fdf5e5d5b78a49b826fcdc0eb2e2aa7191980e3d2cfd2a30303a74f212e2" },
|
||||||
{ file = "msgpack-1.0.7-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:dd632777ff3beaaf629f1ab4396caf7ba0bdd075d948a69460d13d44357aca4c" },
|
{ file = "msgpack-1.0.8-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:6a0e76621f6e1f908ae52860bdcb58e1ca85231a9b0545e64509c931dd34275a" },
|
||||||
{ file = "msgpack-1.0.7-cp38-cp38-win32.whl", hash = "sha256:4e71bc4416de195d6e9b4ee93ad3f2f6b2ce11d042b4d7a7ee00bbe0358bd0c2" },
|
{ file = "msgpack-1.0.8-cp38-cp38-win32.whl", hash = "sha256:374a8e88ddab84b9ada695d255679fb99c53513c0a51778796fcf0944d6c789c" },
|
||||||
{ file = "msgpack-1.0.7-cp38-cp38-win_amd64.whl", hash = "sha256:8f5b234f567cf76ee489502ceb7165c2a5cecec081db2b37e35332b537f8157c" },
|
{ file = "msgpack-1.0.8-cp38-cp38-win_amd64.whl", hash = "sha256:f3709997b228685fe53e8c433e2df9f0cdb5f4542bd5114ed17ac3c0129b0480" },
|
||||||
{ file = "msgpack-1.0.7-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:bfef2bb6ef068827bbd021017a107194956918ab43ce4d6dc945ffa13efbc25f" },
|
{ file = "msgpack-1.0.8-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:f51bab98d52739c50c56658cc303f190785f9a2cd97b823357e7aeae54c8f68a" },
|
||||||
{ file = "msgpack-1.0.7-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:484ae3240666ad34cfa31eea7b8c6cd2f1fdaae21d73ce2974211df099a95d81" },
|
{ file = "msgpack-1.0.8-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:73ee792784d48aa338bba28063e19a27e8d989344f34aad14ea6e1b9bd83f596" },
|
||||||
{ file = "msgpack-1.0.7-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:3967e4ad1aa9da62fd53e346ed17d7b2e922cba5ab93bdd46febcac39be636fc" },
|
{ file = "msgpack-1.0.8-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:f9904e24646570539a8950400602d66d2b2c492b9010ea7e965025cb71d0c86d" },
|
||||||
{ file = "msgpack-1.0.7-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8dd178c4c80706546702c59529ffc005681bd6dc2ea234c450661b205445a34d" },
|
{ file = "msgpack-1.0.8-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e75753aeda0ddc4c28dce4c32ba2f6ec30b1b02f6c0b14e547841ba5b24f753f" },
|
||||||
{ file = "msgpack-1.0.7-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f6ffbc252eb0d229aeb2f9ad051200668fc3a9aaa8994e49f0cb2ffe2b7867e7" },
|
{ file = "msgpack-1.0.8-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5dbf059fb4b7c240c873c1245ee112505be27497e90f7c6591261c7d3c3a8228" },
|
||||||
{ file = "msgpack-1.0.7-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:822ea70dc4018c7e6223f13affd1c5c30c0f5c12ac1f96cd8e9949acddb48a61" },
|
{ file = "msgpack-1.0.8-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:4916727e31c28be8beaf11cf117d6f6f188dcc36daae4e851fee88646f5b6b18" },
|
||||||
{ file = "msgpack-1.0.7-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:384d779f0d6f1b110eae74cb0659d9aa6ff35aaf547b3955abf2ab4c901c4819" },
|
{ file = "msgpack-1.0.8-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:7938111ed1358f536daf311be244f34df7bf3cdedb3ed883787aca97778b28d8" },
|
||||||
{ file = "msgpack-1.0.7-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:f64e376cd20d3f030190e8c32e1c64582eba56ac6dc7d5b0b49a9d44021b52fd" },
|
{ file = "msgpack-1.0.8-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:493c5c5e44b06d6c9268ce21b302c9ca055c1fd3484c25ba41d34476c76ee746" },
|
||||||
{ file = "msgpack-1.0.7-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:5ed82f5a7af3697b1c4786053736f24a0efd0a1b8a130d4c7bfee4b9ded0f08f" },
|
{ file = "msgpack-1.0.8-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:5fbb160554e319f7b22ecf530a80a3ff496d38e8e07ae763b9e82fadfe96f273" },
|
||||||
{ file = "msgpack-1.0.7-cp39-cp39-win32.whl", hash = "sha256:f26a07a6e877c76a88e3cecac8531908d980d3d5067ff69213653649ec0f60ad" },
|
{ file = "msgpack-1.0.8-cp39-cp39-win32.whl", hash = "sha256:f9af38a89b6a5c04b7d18c492c8ccf2aee7048aff1ce8437c4683bb5a1df893d" },
|
||||||
{ file = "msgpack-1.0.7-cp39-cp39-win_amd64.whl", hash = "sha256:1dc93e8e4653bdb5910aed79f11e165c85732067614f180f70534f056da97db3" },
|
{ file = "msgpack-1.0.8-cp39-cp39-win_amd64.whl", hash = "sha256:ed59dd52075f8fc91da6053b12e8c89e37aa043f8986efd89e61fae69dc1b011" },
|
||||||
{ file = "msgpack-1.0.7.tar.gz", hash = "sha256:572efc93db7a4d27e404501975ca6d2d9775705c2d922390d878fcf768d92c87" },
|
{ file = "msgpack-1.0.8-py3-none-any.whl", hash = "sha256:24f727df1e20b9876fa6e95f840a2a2651e34c0ad147676356f4bf5fbb0206ca" },
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
@ -521,13 +521,13 @@ test = ["pytest"]
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "pyright"
|
name = "pyright"
|
||||||
version = "1.1.351"
|
version = "1.1.352"
|
||||||
description = "Command line wrapper for pyright"
|
description = "Command line wrapper for pyright"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.7"
|
python-versions = ">=3.7"
|
||||||
files = [
|
files = [
|
||||||
{ file = "pyright-1.1.351-py3-none-any.whl", hash = "sha256:83b44b25396ae20661fc5f133c3fce30928ff1296d4f2e5ff0bca5fcf03eb89d" },
|
{ file = "pyright-1.1.352-py3-none-any.whl", hash = "sha256:0040cf173c6a60704e553bfd129dfe54de59cc76d0b2b80f77cfab4f50701d64" },
|
||||||
{ file = "pyright-1.1.351.tar.gz", hash = "sha256:01124099714eebd7f6525d8cbfa350626b56dfaf771cfcd55c03e69f0f1efbbd" },
|
{ file = "pyright-1.1.352.tar.gz", hash = "sha256:a621c0dfbcf1291b3610641a07380fefaa1d0e182890a1b2a7f13b446e8109a9" },
|
||||||
]
|
]
|
||||||
|
|
||||||
[package.dependencies]
|
[package.dependencies]
|
||||||
@ -539,13 +539,13 @@ dev = ["twine (>=3.4.1)"]
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "pytest"
|
name = "pytest"
|
||||||
version = "8.0.1"
|
version = "8.0.2"
|
||||||
description = "pytest: simple powerful testing with Python"
|
description = "pytest: simple powerful testing with Python"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.8"
|
python-versions = ">=3.8"
|
||||||
files = [
|
files = [
|
||||||
{ file = "pytest-8.0.1-py3-none-any.whl", hash = "sha256:3e4f16fe1c0a9dc9d9389161c127c3edc5d810c38d6793042fb81d9f48a59fca" },
|
{ file = "pytest-8.0.2-py3-none-any.whl", hash = "sha256:edfaaef32ce5172d5466b5127b42e0d6d35ebbe4453f0e3505d96afd93f6b096" },
|
||||||
{ file = "pytest-8.0.1.tar.gz", hash = "sha256:267f6563751877d772019b13aacbe4e860d73fe8f651f28112e9ac37de7513ae" },
|
{ file = "pytest-8.0.2.tar.gz", hash = "sha256:d4051d623a2e0b7e51960ba963193b09ce6daeb9759a451844a21e4ddedfc1bd" },
|
||||||
]
|
]
|
||||||
|
|
||||||
[package.dependencies]
|
[package.dependencies]
|
||||||
@ -791,28 +791,28 @@ files = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "ruff"
|
name = "ruff"
|
||||||
version = "0.2.2"
|
version = "0.3.0"
|
||||||
description = "An extremely fast Python linter and code formatter, written in Rust."
|
description = "An extremely fast Python linter and code formatter, written in Rust."
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.7"
|
python-versions = ">=3.7"
|
||||||
files = [
|
files = [
|
||||||
{ file = "ruff-0.2.2-py3-none-macosx_10_12_x86_64.macosx_11_0_arm64.macosx_10_12_universal2.whl", hash = "sha256:0a9efb032855ffb3c21f6405751d5e147b0c6b631e3ca3f6b20f917572b97eb6" },
|
{ file = "ruff-0.3.0-py3-none-macosx_10_12_x86_64.macosx_11_0_arm64.macosx_10_12_universal2.whl", hash = "sha256:7deb528029bacf845bdbb3dbb2927d8ef9b4356a5e731b10eef171e3f0a85944" },
|
||||||
{ file = "ruff-0.2.2-py3-none-macosx_10_12_x86_64.whl", hash = "sha256:d450b7fbff85913f866a5384d8912710936e2b96da74541c82c1b458472ddb39" },
|
{ file = "ruff-0.3.0-py3-none-macosx_10_12_x86_64.whl", hash = "sha256:e1e0d4381ca88fb2b73ea0766008e703f33f460295de658f5467f6f229658c19" },
|
||||||
{ file = "ruff-0.2.2-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ecd46e3106850a5c26aee114e562c329f9a1fbe9e4821b008c4404f64ff9ce73" },
|
{ file = "ruff-0.3.0-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:2f7dbba46e2827dfcb0f0cc55fba8e96ba7c8700e0a866eb8cef7d1d66c25dcb" },
|
||||||
{ file = "ruff-0.2.2-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:5e22676a5b875bd72acd3d11d5fa9075d3a5f53b877fe7b4793e4673499318ba" },
|
{ file = "ruff-0.3.0-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:23dbb808e2f1d68eeadd5f655485e235c102ac6f12ad31505804edced2a5ae77" },
|
||||||
{ file = "ruff-0.2.2-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:1695700d1e25a99d28f7a1636d85bafcc5030bba9d0578c0781ba1790dbcf51c" },
|
{ file = "ruff-0.3.0-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:3ef655c51f41d5fa879f98e40c90072b567c666a7114fa2d9fe004dffba00932" },
|
||||||
{ file = "ruff-0.2.2-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:b0c232af3d0bd8f521806223723456ffebf8e323bd1e4e82b0befb20ba18388e" },
|
{ file = "ruff-0.3.0-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:d0d3d7ef3d4f06433d592e5f7d813314a34601e6c5be8481cccb7fa760aa243e" },
|
||||||
{ file = "ruff-0.2.2-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:f63d96494eeec2fc70d909393bcd76c69f35334cdbd9e20d089fb3f0640216ca" },
|
{ file = "ruff-0.3.0-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:b08b356d06a792e49a12074b62222f9d4ea2a11dca9da9f68163b28c71bf1dd4" },
|
||||||
{ file = "ruff-0.2.2-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:6a61ea0ff048e06de273b2e45bd72629f470f5da8f71daf09fe481278b175001" },
|
{ file = "ruff-0.3.0-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:9343690f95710f8cf251bee1013bf43030072b9f8d012fbed6ad702ef70d360a" },
|
||||||
{ file = "ruff-0.2.2-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5e1439c8f407e4f356470e54cdecdca1bd5439a0673792dbe34a2b0a551a2fe3" },
|
{ file = "ruff-0.3.0-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a1f3ed501a42f60f4dedb7805fa8d4534e78b4e196f536bac926f805f0743d49" },
|
||||||
{ file = "ruff-0.2.2-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:940de32dc8853eba0f67f7198b3e79bc6ba95c2edbfdfac2144c8235114d6726" },
|
{ file = "ruff-0.3.0-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:cc30a9053ff2f1ffb505a585797c23434d5f6c838bacfe206c0e6cf38c921a1e" },
|
||||||
{ file = "ruff-0.2.2-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:0c126da55c38dd917621552ab430213bdb3273bb10ddb67bc4b761989210eb6e" },
|
{ file = "ruff-0.3.0-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:5da894a29ec018a8293d3d17c797e73b374773943e8369cfc50495573d396933" },
|
||||||
{ file = "ruff-0.2.2-py3-none-musllinux_1_2_i686.whl", hash = "sha256:3b65494f7e4bed2e74110dac1f0d17dc8e1f42faaa784e7c58a98e335ec83d7e" },
|
{ file = "ruff-0.3.0-py3-none-musllinux_1_2_i686.whl", hash = "sha256:755c22536d7f1889be25f2baf6fedd019d0c51d079e8417d4441159f3bcd30c2" },
|
||||||
{ file = "ruff-0.2.2-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:1ec49be4fe6ddac0503833f3ed8930528e26d1e60ad35c2446da372d16651ce9" },
|
{ file = "ruff-0.3.0-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:dd73fe7f4c28d317855da6a7bc4aa29a1500320818dd8f27df95f70a01b8171f" },
|
||||||
{ file = "ruff-0.2.2-py3-none-win32.whl", hash = "sha256:d920499b576f6c68295bc04e7b17b6544d9d05f196bb3aac4358792ef6f34325" },
|
{ file = "ruff-0.3.0-py3-none-win32.whl", hash = "sha256:19eacceb4c9406f6c41af806418a26fdb23120dfe53583df76d1401c92b7c14b" },
|
||||||
{ file = "ruff-0.2.2-py3-none-win_amd64.whl", hash = "sha256:cc9a91ae137d687f43a44c900e5d95e9617cb37d4c989e462980ba27039d239d" },
|
{ file = "ruff-0.3.0-py3-none-win_amd64.whl", hash = "sha256:128265876c1d703e5f5e5a4543bd8be47c73a9ba223fd3989d4aa87dd06f312f" },
|
||||||
{ file = "ruff-0.2.2-py3-none-win_arm64.whl", hash = "sha256:c9d15fc41e6054bfc7200478720570078f0b41c9ae4f010bcc16bd6f4d1aacdd" },
|
{ file = "ruff-0.3.0-py3-none-win_arm64.whl", hash = "sha256:e3a4a6d46aef0a84b74fcd201a4401ea9a6cd85614f6a9435f2d33dd8cefbf83" },
|
||||||
{ file = "ruff-0.2.2.tar.gz", hash = "sha256:e62ed7f36b3068a30ba39193a14274cd706bc486fad521276458022f7bccb31d" },
|
{ file = "ruff-0.3.0.tar.gz", hash = "sha256:0886184ba2618d815067cf43e005388967b67ab9c80df52b32ec1152ab49f53a" },
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
@ -963,5 +963,5 @@ test = ["pytest (>=6.0.0)", "setuptools (>=65)"]
|
|||||||
|
|
||||||
[metadata]
|
[metadata]
|
||||||
lock-version = "2.0"
|
lock-version = "2.0"
|
||||||
python-versions = "^3.10"
|
python-versions = "^3.9"
|
||||||
content-hash = "ad7bc225fd2048867bce6d5b96c739554d4b7a16bd035a60e4d7d2d82ecd7811"
|
content-hash = "262b669a592c5e0c92f1d59ebc67df0a9549ff54d2c45baff168478fdce76c1b"
|
||||||
|
@ -4,7 +4,7 @@ build-backend = "poetry.core.masonry.api"
|
|||||||
|
|
||||||
[tool.poetry]
|
[tool.poetry]
|
||||||
name = "comicfn2dict"
|
name = "comicfn2dict"
|
||||||
version = "0.2.0a0"
|
version = "0.2.1"
|
||||||
description = "Parse common comic filenames and return a dict of metadata attributes. Includes a cli."
|
description = "Parse common comic filenames and return a dict of metadata attributes. Includes a cli."
|
||||||
license = "GPL-3.0-only"
|
license = "GPL-3.0-only"
|
||||||
authors = ["AJ Slater <aj@slater.net>"]
|
authors = ["AJ Slater <aj@slater.net>"]
|
||||||
@ -28,7 +28,7 @@ exclude = ["*/**/*~"]
|
|||||||
include = []
|
include = []
|
||||||
|
|
||||||
[tool.poetry.dependencies]
|
[tool.poetry.dependencies]
|
||||||
python = "^3.10"
|
python = "^3.9"
|
||||||
|
|
||||||
[tool.poetry.group.dev.dependencies]
|
[tool.poetry.group.dev.dependencies]
|
||||||
neovim = "^0.3.1"
|
neovim = "^0.3.1"
|
||||||
@ -45,7 +45,7 @@ pytest-gitignore = "^1.3"
|
|||||||
codespell = "^2.1.0"
|
codespell = "^2.1.0"
|
||||||
pyright = "^1.1.232"
|
pyright = "^1.1.232"
|
||||||
radon = { version = "^6.0.1", extras = ["toml"] }
|
radon = { version = "^6.0.1", extras = ["toml"] }
|
||||||
ruff = "^0.2.1"
|
ruff = "^0.3.0"
|
||||||
types-python-dateutil = "^2.8.19"
|
types-python-dateutil = "^2.8.19"
|
||||||
vulture = "^2.3"
|
vulture = "^2.3"
|
||||||
|
|
||||||
@ -125,7 +125,7 @@ exclude = "*~,.git/*,.mypy_cache/*,.pytest_cache/*,.venv*,__pycache__/*,cache/*,
|
|||||||
extend-exclude = ["typings"]
|
extend-exclude = ["typings"]
|
||||||
target-version = "py310"
|
target-version = "py310"
|
||||||
|
|
||||||
[tool.lint.ruff]
|
[tool.ruff.lint]
|
||||||
extend-ignore = [
|
extend-ignore = [
|
||||||
"S101",
|
"S101",
|
||||||
"D203",
|
"D203",
|
||||||
|
@ -2,7 +2,6 @@
|
|||||||
|
|
||||||
from types import MappingProxyType
|
from types import MappingProxyType
|
||||||
|
|
||||||
|
|
||||||
TEST_COMIC_FIELDS = {
|
TEST_COMIC_FIELDS = {
|
||||||
"series": "Long Series Name",
|
"series": "Long Series Name",
|
||||||
"issue": "001",
|
"issue": "001",
|
||||||
@ -56,11 +55,6 @@ FNS = {
|
|||||||
"Long Series Name #001 (2000) Title (TPB) (Releaser).cbz": TEST_COMIC_FIELDS,
|
"Long Series Name #001 (2000) Title (TPB) (Releaser).cbz": TEST_COMIC_FIELDS,
|
||||||
"Long Series Name (2000) 001 Title (TPB) (Releaser).cbz": TEST_COMIC_FIELDS,
|
"Long Series Name (2000) 001 Title (TPB) (Releaser).cbz": TEST_COMIC_FIELDS,
|
||||||
"Long Series Name (2000) #001 Title (TPB) (Releaser).cbz": TEST_COMIC_FIELDS,
|
"Long Series Name (2000) #001 Title (TPB) (Releaser).cbz": TEST_COMIC_FIELDS,
|
||||||
"Long Series Name v1 (2000) #001 "
|
|
||||||
"Title (TPB) (Releaser).cbz": TEST_COMIC_FIELDS_VOL,
|
|
||||||
"Long Series Name 001 (2000) (TPB-Releaser) Title.cbz": TEST_COMIC_FIELDS,
|
|
||||||
"Long Series Name Vol 1 "
|
|
||||||
"(2000) (TPB) (Releaser & Releaser-Releaser) Title.cbr": TEST_COMIC_VOL_ONLY,
|
|
||||||
"Ultimate Craziness (2019) (Digital) (Friends-of-Bill).cbr": {
|
"Ultimate Craziness (2019) (Digital) (Friends-of-Bill).cbr": {
|
||||||
"series": "Ultimate Craziness",
|
"series": "Ultimate Craziness",
|
||||||
"year": "2019",
|
"year": "2019",
|
||||||
@ -443,6 +437,41 @@ FNS.update(
|
|||||||
"restored) (Shadowcat-Empire)",
|
"restored) (Shadowcat-Empire)",
|
||||||
),
|
),
|
||||||
},
|
},
|
||||||
|
"Captain Science #001 (1950) The Beginning - nothing.cbz": {
|
||||||
|
"ext": "cbz",
|
||||||
|
"issue": "001",
|
||||||
|
"title": "The Beginning - nothing",
|
||||||
|
"series": "Captain Science",
|
||||||
|
"year": "1950",
|
||||||
|
},
|
||||||
|
"Captain Science #001-cix-cbi.cbr": {
|
||||||
|
"ext": "cbr",
|
||||||
|
"issue": "001",
|
||||||
|
"series": "Captain Science",
|
||||||
|
"title": "cix-cbi",
|
||||||
|
},
|
||||||
|
"Long Series Name v1 (2000) #001 "
|
||||||
|
"Title (TPB) (Releaser).cbz": TEST_COMIC_FIELDS_VOL,
|
||||||
|
"Long Series Name 001 (2000) (TPB-Releaser) Title.cbz": {
|
||||||
|
"series": "Long Series Name",
|
||||||
|
"issue": "001",
|
||||||
|
"year": "2000",
|
||||||
|
"original_format": "TPB",
|
||||||
|
"scan_info": "Releaser",
|
||||||
|
"remainders": ("Title",),
|
||||||
|
"ext": "cbz",
|
||||||
|
},
|
||||||
|
"Long Series Name Vol 1 "
|
||||||
|
"(2000) (TPB) (Releaser & Releaser-Releaser) Title.cbr": {
|
||||||
|
"series": "Long Series Name",
|
||||||
|
"volume": "1",
|
||||||
|
"issue": "1",
|
||||||
|
"remainders": ("Title",),
|
||||||
|
"original_format": "TPB",
|
||||||
|
"year": "2000",
|
||||||
|
"scan_info": "Releaser & Releaser-Releaser",
|
||||||
|
"ext": "cbr",
|
||||||
|
},
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
"""Tests for filename parsing."""
|
"""Tests for filename parsing."""
|
||||||
|
|
||||||
from pprint import pprint
|
from pprint import pprint
|
||||||
|
|
||||||
import pytest
|
import pytest
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
"""Tests for filename parsing."""
|
"""Tests for filename parsing."""
|
||||||
|
|
||||||
import pytest
|
import pytest
|
||||||
|
|
||||||
from comicfn2dict import ComicFilenameSerializer
|
from comicfn2dict import ComicFilenameSerializer
|
||||||
|
Reference in New Issue
Block a user