Skip to content

Commit 1dfd0b0

Browse files
authored
Merge pull request #151 from sandialabs/drop-support-for-python-3.8
chore!: Drop support for Python 3.8
2 parents 08719d1 + f9ec075 commit 1dfd0b0

File tree

9 files changed

+35
-29
lines changed

9 files changed

+35
-29
lines changed

.github/workflows/continuous-integration.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ jobs:
1919
runs-on: macos-latest
2020
strategy:
2121
matrix:
22-
version: ["3.8", "3.9", "3.10", "3.11", "3.12"]
22+
version: ["3.9", "3.10", "3.11", "3.12"]
2323
steps:
2424

2525
- name: Harden Runner

README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@
1515
[![pre-commit.ci Status](https://results.pre-commit.ci/badge/github/sandialabs/shell-logger/master.svg)](https://results.pre-commit.ci/latest/github/sandialabs/shell-logger/master)
1616
[![PyPI - Version](https://img.shields.io/pypi/v/shell-logger-sandialabs?label=PyPI)](https://pypi.org/project/shell-logger-sandialabs/)
1717
![PyPI - Downloads](https://img.shields.io/pypi/dm/shell-logger-sandialabs?label=PyPI%20downloads)
18-
![Python Version](https://img.shields.io/badge/Python-3.8|3.9|3.10|3.11|3.12-blue.svg)
18+
![Python Version](https://img.shields.io/badge/Python-3.9|3.10|3.11|3.12-blue.svg)
1919
[![Ruff](https://img.shields.io/endpoint?url=https://raw.githubusercontent.com/astral-sh/ruff/main/assets/badge/v2.json)](https://github.com/astral-sh/ruff)
2020

2121
> **NOTICE:** After using this package for a few years, we realized we'd

doc/source/index.rst

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -64,7 +64,7 @@ shell-logger
6464
.. |PyPI Version| image:: https://img.shields.io/pypi/v/shell-logger-sandialabs?label=PyPI
6565
:target: https://pypi.org/project/shell-logger-sandialabs/
6666
.. |PyPI Downloads| image:: https://img.shields.io/pypi/dm/shell-logger-sandialabs?label=PyPI%20downloads
67-
.. |Python Version| image:: https://img.shields.io/badge/Python-3.8|3.9|3.10|3.11|3.12-blue.svg
67+
.. |Python Version| image:: https://img.shields.io/badge/Python-3.9|3.10|3.11|3.12-blue.svg
6868
.. |Ruff| image:: https://img.shields.io/endpoint?url=https://raw.githubusercontent.com/astral-sh/ruff/main/assets/badge/v2.json
6969
:target: https://github.com/astral-sh/ruff
7070

pyproject.toml

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,6 @@ classifiers = [
2828
"Operating System :: POSIX",
2929
"Programming Language :: Python :: 3",
3030
"Programming Language :: Python :: 3 :: Only",
31-
"Programming Language :: Python :: 3.8",
3231
"Programming Language :: Python :: 3.9",
3332
"Programming Language :: Python :: 3.10",
3433
"Programming Language :: Python :: 3.11",

shell_logger/html_utilities.py

Lines changed: 15 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@
1313
from datetime import datetime
1414
from pathlib import Path
1515
from types import SimpleNamespace
16-
from typing import Iterator, List, TextIO, Tuple, Union
16+
from typing import Iterator, TextIO, Union
1717

1818

1919
def nested_simplenamespace_to_dict(
@@ -157,7 +157,7 @@ def flatten(element: Union[str, bytes, Iterable]) -> Iterator[str]:
157157

158158

159159
def parent_logger_card_html(
160-
name: str, *args: List[Iterator[str]]
160+
name: str, *args: list[Iterator[str]]
161161
) -> Iterator[str]:
162162
"""
163163
Generate the HTML for a parent logger card.
@@ -212,7 +212,7 @@ def child_logger_card(log) -> Iterator[str]:
212212

213213

214214
def child_logger_card_html(
215-
name: str, duration: str, *args: Union[Iterator[str], List[Iterator[str]]]
215+
name: str, duration: str, *args: Union[Iterator[str], list[Iterator[str]]]
216216
) -> Iterator[str]:
217217
"""
218218
Generate the HTML for a child logger card.
@@ -480,7 +480,7 @@ def command_card(log: dict, stream_dir: Path) -> Iterator[str]:
480480

481481

482482
def time_series_plot(
483-
cmd_id: str, data_tuples: List[Tuple[float, float]], series_title: str
483+
cmd_id: str, data_tuples: list[tuple[float, float]], series_title: str
484484
) -> Iterator[str]:
485485
"""
486486
Create the HTML for a plot of time series data.
@@ -501,7 +501,7 @@ def time_series_plot(
501501

502502

503503
def disk_time_series_plot(
504-
cmd_id: str, data_tuples: Tuple[float, float], volume_name: str
504+
cmd_id: str, data_tuples: list[tuple[float, float]], volume_name: str
505505
) -> Iterator[str]:
506506
"""
507507
Generate a time series plot of disk usage.
@@ -530,7 +530,7 @@ def disk_time_series_plot(
530530

531531

532532
def stat_chart_card(
533-
labels: List[str], data: List[float], title: str, identifier: str
533+
labels: list[str], data: list[float], title: str, identifier: str
534534
) -> Iterator[str]:
535535
"""
536536
Create the HTML for a two-dimensional plot.
@@ -676,7 +676,7 @@ def output_block_html(
676676

677677
def split_template(
678678
template: str, split_at: str, **kwargs
679-
) -> Tuple[str, str, str]:
679+
) -> tuple[str, str, str]:
680680
"""
681681
Subdivide a HTML template.
682682
@@ -854,7 +854,7 @@ def sgr_4bit_color_and_style_to_html(sgr: str) -> str:
854854
return f'<span style="{sgr_to_css.get(sgr) or str()}">'
855855

856856

857-
def sgr_8bit_color_to_html(sgr_params: List[str]) -> str: # noqa: PLR0911
857+
def sgr_8bit_color_to_html(sgr_params: list[str]) -> str: # noqa: PLR0911
858858
"""
859859
Convert 8-bit SGR colors to HTML.
860860
@@ -866,6 +866,10 @@ def sgr_8bit_color_to_html(sgr_params: List[str]) -> str: # noqa: PLR0911
866866
867867
Returns:
868868
A HTML ``span`` with the appropriate CSS style.
869+
870+
Raises:
871+
RuntimeError: If the code somehow falls through all the `if`
872+
blocks without returning. This should never happen.
869873
"""
870874
sgr_256 = int(sgr_params[2]) if len(sgr_params) > 2 else 0
871875
if sgr_256 < 0 or sgr_256 > 255 or not sgr_params:
@@ -891,10 +895,11 @@ def sgr_8bit_color_to_html(sgr_params: List[str]) -> str: # noqa: PLR0911
891895
return sgr_4bit_color_and_style_to_html(str(40 + sgr_256))
892896
if sgr_256 < 16:
893897
return sgr_4bit_color_and_style_to_html(str(92 + sgr_256))
894-
return "THIS SHOULD NEVER HAPPEN"
898+
message = "THIS SHOULD NEVER HAPPEN"
899+
raise RuntimeError(message)
895900

896901

897-
def sgr_24bit_color_to_html(sgr_params: List[str]) -> str:
902+
def sgr_24bit_color_to_html(sgr_params: list[str]) -> str:
898903
"""
899904
Convert 24-bit SGR colors to HTML.
900905

shell_logger/shell.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@
1818
from threading import Thread
1919
from time import time
2020
from types import SimpleNamespace
21-
from typing import IO, List, Optional, TextIO, Tuple
21+
from typing import IO, Optional, TextIO
2222

2323

2424
END_OF_READ = 4
@@ -262,7 +262,7 @@ def tee( # noqa: C901
262262
stdout_tee = [sys_stdout, stdout_io, stdout_path]
263263
stderr_tee = [sys_stderr, stderr_io, stderr_path]
264264

265-
def write(input_file: TextIO, output_files: List[TextIO]) -> None:
265+
def write(input_file: TextIO, output_files: list[TextIO]) -> None:
266266
"""
267267
Write an input to multiple outputs.
268268
@@ -320,7 +320,7 @@ def write(input_file: TextIO, output_files: List[TextIO]) -> None:
320320

321321
def auxiliary_command(
322322
self, **kwargs
323-
) -> Tuple[Optional[str], Optional[str]]:
323+
) -> tuple[Optional[str], Optional[str]]:
324324
"""
325325
Run auxiliary commands like `umask`, `pwd`, `env`, etc.
326326

shell_logger/shell_logger.py

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@
1919
from distutils import dir_util
2020
from pathlib import Path
2121
from types import SimpleNamespace
22-
from typing import Iterator, List, Optional, Union
22+
from typing import Iterator, Optional, Union
2323

2424
from .html_utilities import (
2525
append_html,
@@ -139,7 +139,7 @@ def __init__( # noqa: PLR0913
139139
html_file: Optional[Path] = None,
140140
indent: int = 0,
141141
login_shell: bool = False,
142-
log: Optional[List[object]] = None,
142+
log: Optional[list[object]] = None,
143143
init_time: Optional[datetime] = None,
144144
done_time: Optional[datetime] = None,
145145
duration: Optional[str] = None,
@@ -179,7 +179,7 @@ def __init__( # noqa: PLR0913
179179
generally be omitted.
180180
"""
181181
self.name = name
182-
self.log_book: List[Union[dict, ShellLogger]] = (
182+
self.log_book: list[Union[dict, ShellLogger]] = (
183183
log if log is not None else []
184184
)
185185
self.init_time = datetime.now() if init_time is None else init_time
@@ -404,7 +404,7 @@ def html_print(self, msg: str, msg_title: str = "HTML Message") -> None:
404404
}
405405
self.log_book.append(log)
406406

407-
def to_html(self) -> Union[Iterator[str], List[Iterator[str]]]:
407+
def to_html(self) -> Union[Iterator[str], list[Iterator[str]]]:
408408
"""
409409
Convert the log entries to HTML.
410410
@@ -591,7 +591,7 @@ def log( # noqa: PLR0913
591591
s = int(result.wall / 1000) % 60
592592
log["duration"] = f"{h}h {m}m {s}s"
593593
log["return_code"] = result.returncode
594-
log = {**log, **nested_simplenamespace_to_dict(result)}
594+
log |= nested_simplenamespace_to_dict(result)
595595
self.log_book.append(log)
596596
return {
597597
"return_code": log["return_code"],

shell_logger/stats_collector.py

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@
1313
from multiprocessing import Manager, Process
1414
from pathlib import Path
1515
from time import sleep, time
16-
from typing import List, Tuple, TYPE_CHECKING
16+
from typing import TYPE_CHECKING
1717

1818
from .abstract_method import AbstractMethod
1919

@@ -26,7 +26,7 @@
2626
psutil = None
2727

2828

29-
def stats_collectors(**kwargs) -> List[StatsCollector]:
29+
def stats_collectors(**kwargs) -> list[StatsCollector]:
3030
"""
3131
Generate stats collectors.
3232
@@ -236,7 +236,7 @@ def collect(self) -> None:
236236
timestamp = round(time() * milliseconds_per_second)
237237
self.stats.append((timestamp, psutil.cpu_percent(interval=None)))
238238

239-
def unproxied_stats(self) -> List[Tuple[float, float]]:
239+
def unproxied_stats(self) -> list[tuple[float, float]]:
240240
"""
241241
Convert the statistics to standard Python data types.
242242
@@ -277,7 +277,7 @@ def collect(self) -> None:
277277
timestamp = round(time() * milliseconds_per_second)
278278
self.stats.append((timestamp, psutil.virtual_memory().percent))
279279

280-
def unproxied_stats(self) -> List[Tuple[float, float]]:
280+
def unproxied_stats(self) -> list[tuple[float, float]]:
281281
"""
282282
Convert the statistics to standard Python data types.
283283

test/test_shell_logger.py

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -64,9 +64,11 @@ def shell_logger() -> ShellLogger:
6464
measure = ["cpu", "memory", "disk"]
6565
kwargs = {"measure": measure, "return_info": True, "interval": 0.1}
6666
if os.uname().sysname == "Linux":
67-
kwargs.update(
68-
{"trace": "ltrace", "expression": "setlocale", "summary": True}
69-
)
67+
kwargs |= {
68+
"trace": "ltrace",
69+
"expression": "setlocale",
70+
"summary": True,
71+
}
7072
else:
7173
print(
7274
f"Warning: uname is not 'Linux': {os.uname()}; ltrace not tested."

0 commit comments

Comments
 (0)