update compat
This commit is contained in:
commit
502885fd23
57
.github/workflows/ci.yml
vendored
Normal file
57
.github/workflows/ci.yml
vendored
Normal file
@ -0,0 +1,57 @@
|
||||
name: CI
|
||||
|
||||
on:
|
||||
pull_request: {}
|
||||
push: {}
|
||||
|
||||
jobs:
|
||||
lint:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- name: Set up Python 3
|
||||
uses: actions/setup-python@v2
|
||||
with:
|
||||
python-version: '3.x'
|
||||
- name: Install dependencies
|
||||
run: |
|
||||
python3 -m pip install --upgrade pip
|
||||
python3 -m pip install tox tox-gh-actions
|
||||
- run: tox -e lint
|
||||
|
||||
check-docs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- name: Set up Python 3
|
||||
uses: actions/setup-python@v2
|
||||
with:
|
||||
python-version: '3.x'
|
||||
- name: Install dependencies
|
||||
run: |
|
||||
python3 -m pip install --upgrade pip
|
||||
python3 -m pip install tox tox-gh-actions
|
||||
- run: tox -e check-docs
|
||||
|
||||
test:
|
||||
runs-on: ubuntu-latest
|
||||
continue-on-error: ${{ matrix.experimental }}
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
python-version: ["3.7", "3.8", "3.9", "3.10", "3.11"]
|
||||
experimental: [false]
|
||||
include:
|
||||
- python-version: "3.12-dev"
|
||||
experimental: true
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- name: Set up Python ${{ matrix.python-version }}
|
||||
uses: actions/setup-python@v2
|
||||
with:
|
||||
python-version: ${{ matrix.python-version }}
|
||||
- name: Install dependencies
|
||||
run: |
|
||||
python3 -m pip install --upgrade pip setuptools
|
||||
python3 -m pip install tox tox-gh-actions
|
||||
- run: tox
|
6
Makefile
6
Makefile
@ -9,7 +9,7 @@ lint:
|
||||
|
||||
.PHONY: test
|
||||
test:
|
||||
coverage run -m py.test
|
||||
coverage run -m pytest
|
||||
coverage report
|
||||
|
||||
.PHONY: clean
|
||||
@ -49,15 +49,11 @@ check-docs:
|
||||
deb-local: clean sdist
|
||||
docker build -t afancontrol-debuild -f ./Dockerfile.debian .
|
||||
docker run -it --rm \
|
||||
-e DEBFULLNAME="`git config --global user.name`" \
|
||||
-e DEBEMAIL="`git config --global user.email`" \
|
||||
-v `pwd`/dist:/afancontrol/dist \
|
||||
-v `pwd`/debian:/afancontrol/debian \
|
||||
afancontrol-debuild sh -ex -c '\
|
||||
tar xaf /afancontrol/dist/afancontrol-*.tar.gz --strip 1; \
|
||||
dch -v `python3 setup.py --version` -b --distribution=unstable; \
|
||||
debuild -us -uc -b; \
|
||||
cp debian/changelog /afancontrol/debian/; \
|
||||
cd ../; \
|
||||
ls -alh; \
|
||||
mkdir /afancontrol/dist/debian; \
|
||||
|
@ -5,8 +5,8 @@ afancontrol
|
||||
:target: https://pypi.python.org/pypi/afancontrol/
|
||||
:alt: Latest Version
|
||||
|
||||
.. image:: https://img.shields.io/travis/KostyaEsmukov/afancontrol.svg?style=flat-square
|
||||
:target: https://travis-ci.org/KostyaEsmukov/afancontrol
|
||||
.. image:: https://img.shields.io/github/workflow/status/KostyaEsmukov/afancontrol/CI?style=flat-square
|
||||
:target: https://github.com/KostyaEsmukov/afancontrol/actions
|
||||
:alt: Build Status
|
||||
|
||||
.. image:: https://img.shields.io/github/license/KostyaEsmukov/afancontrol.svg?style=flat-square
|
||||
|
19
debian/changelog
vendored
19
debian/changelog
vendored
@ -1,3 +1,22 @@
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
afancontrol (3.1.0-1) unstable; urgency=medium
|
||||
|
||||
[ Juha Yrjölä ]
|
||||
* Support glob expansion with fans (#9)
|
||||
|
||||
[ Kostya Esmukov ]
|
||||
* Drop Python 3.6 support, add 3.11
|
||||
|
||||
-- Kostya Esmukov <kostya@esmukov.ru> Mon, 28 Nov 2022 00:11:43 +0200
|
||||
|
||||
afancontrol (3.0.0-2) unstable; urgency=medium
|
||||
|
||||
* Bump debhelper compat to 13
|
||||
|
||||
-- Kostya Esmukov <kostya@esmukov.ru> Mon, 02 Aug 2021 19:19:34 +0000
|
||||
|
||||
>>>>>>> upstream/3.1.0
|
||||
afancontrol (3.0.0-1) unstable; urgency=medium
|
||||
|
||||
* Drop support for prometheus-client < 0.1.0 (debian stretch)
|
||||
|
1
debian/compat
vendored
1
debian/compat
vendored
@ -1 +0,0 @@
|
||||
9
|
28
debian/control
vendored
28
debian/control
vendored
@ -2,37 +2,43 @@ Source: afancontrol
|
||||
Section: utils
|
||||
Priority: optional
|
||||
Maintainer: Kostya Esmukov <kostya@esmukov.ru>
|
||||
Build-Depends: debhelper (>= 9),
|
||||
Build-Depends: debhelper-compat (= 13),
|
||||
dh-python,
|
||||
debhelper (>= 9.20160709) | dh-systemd,
|
||||
python3-all,
|
||||
python3-click,
|
||||
python3-prometheus-client (>= 0.1.0),
|
||||
python3-pytest,
|
||||
python3-requests,
|
||||
python3-serial,
|
||||
python3-setuptools
|
||||
<<<<<<< HEAD
|
||||
Build-Depends-Indep: python3-pytest,
|
||||
python3-requests,
|
||||
python3-click,
|
||||
python3-prometheus-client (>= 0.1.0),
|
||||
python3-serial
|
||||
=======
|
||||
>>>>>>> upstream/3.1.0
|
||||
Standards-Version: 3.9.8
|
||||
Homepage: https://github.com/KostyaEsmukov/afancontrol
|
||||
X-Python3-Version: >= 3.5
|
||||
#Vcs-Git: https://anonscm.debian.org/git/python-modules/packages/python3-afancontrol.git
|
||||
#Vcs-Browser: https://anonscm.debian.org/cgit/python-modules/packages/python3-afancontrol.git/
|
||||
#Testsuite: autopkgtest-pkg-python
|
||||
|
||||
|
||||
Package: afancontrol
|
||||
Architecture: all
|
||||
Depends: ${python3:Depends},
|
||||
${misc:Depends},
|
||||
hddtemp,
|
||||
Depends: hddtemp,
|
||||
lm-sensors,
|
||||
python3-click,
|
||||
python3-pkg-resources,
|
||||
python3-prometheus-client (>= 0.1.0),
|
||||
<<<<<<< HEAD
|
||||
python3-serial
|
||||
Suggests: freeipmi-tools,
|
||||
=======
|
||||
python3-serial,
|
||||
${misc:Depends},
|
||||
${python3:Depends}
|
||||
Suggests: freeipmi-tools
|
||||
>>>>>>> upstream/3.1.0
|
||||
Description: Advanced Fan Control program (Python 3)
|
||||
afancontrol is an Advanced Fan Control program, which controls PWM
|
||||
fans according to the current temperatures of the system components.
|
||||
.
|
||||
This package installs the library for Python 3.
|
||||
|
0
debian/rules
vendored
Normal file → Executable file
0
debian/rules
vendored
Normal file → Executable file
25
setup.cfg
25
setup.cfg
@ -25,13 +25,16 @@ per-file-ignores =
|
||||
src/afancontrol/config.py:C901
|
||||
|
||||
[isort]
|
||||
; https://github.com/timothycrosley/isort#multi-line-output-modes
|
||||
multi_line_output = 3
|
||||
<<<<<<< HEAD
|
||||
; https://github.com/ambv/black#how-black-wraps-lines
|
||||
include_trailing_comma = True
|
||||
force_grid_wrap = 0
|
||||
combine_as_imports = True
|
||||
line_length = 88
|
||||
=======
|
||||
profile = black
|
||||
>>>>>>> upstream/3.1.0
|
||||
|
||||
[metadata]
|
||||
author = Kostya Esmukov
|
||||
@ -45,10 +48,13 @@ classifier =
|
||||
Programming Language :: Python
|
||||
Programming Language :: Python :: 3
|
||||
Programming Language :: Python :: 3 :: Only
|
||||
<<<<<<< HEAD
|
||||
Programming Language :: Python :: 3.6
|
||||
Programming Language :: Python :: 3.7
|
||||
Programming Language :: Python :: 3.8
|
||||
Programming Language :: Python :: 3.9
|
||||
=======
|
||||
>>>>>>> upstream/3.1.0
|
||||
Topic :: System :: Hardware
|
||||
Topic :: System :: Monitoring
|
||||
Topic :: System :: Systems Administration
|
||||
@ -76,7 +82,11 @@ install_requires =
|
||||
package_dir =
|
||||
= src
|
||||
packages = find:
|
||||
<<<<<<< HEAD
|
||||
python_requires = >=3.6
|
||||
=======
|
||||
python_requires = >=3.7
|
||||
>>>>>>> upstream/3.1.0
|
||||
|
||||
[options.entry_points]
|
||||
console_scripts =
|
||||
@ -88,6 +98,7 @@ arduino =
|
||||
metrics =
|
||||
prometheus-client>=0.1.0
|
||||
dev =
|
||||
<<<<<<< HEAD
|
||||
black==20.8b1
|
||||
coverage==5.3
|
||||
flake8==3.8.4
|
||||
@ -97,6 +108,18 @@ dev =
|
||||
requests
|
||||
sphinx==3.2.1
|
||||
wheel
|
||||
=======
|
||||
black==22.10.0
|
||||
coverage==6.5.0
|
||||
flake8==5.0.4
|
||||
isort==5.10.1
|
||||
mypy==0.990
|
||||
pytest==7.2.0
|
||||
sphinx==4.3.2
|
||||
vcrpy==4.2.1
|
||||
requests
|
||||
types-requests
|
||||
>>>>>>> upstream/3.1.0
|
||||
|
||||
[options.packages.find]
|
||||
where = src
|
||||
|
@ -1 +1,5 @@
|
||||
<<<<<<< HEAD
|
||||
__version__ = "3.0.0"
|
||||
=======
|
||||
__version__ = "3.1.0"
|
||||
>>>>>>> upstream/3.1.0
|
||||
|
@ -1,4 +1,8 @@
|
||||
import configparser
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
import glob
|
||||
>>>>>>> upstream/3.1.0
|
||||
from typing import Any, Generic, Iterator, Optional, Type, TypeVar, Union, overload
|
||||
|
||||
T = TypeVar("T", bound=str)
|
||||
@ -127,3 +131,15 @@ class ConfigParserSection(Generic[T]):
|
||||
"[%s] %r option is expected to be set" % (self.__section.name, option)
|
||||
)
|
||||
return res
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
|
||||
|
||||
def expand_glob(path: str):
|
||||
matches = glob.glob(path)
|
||||
if not matches:
|
||||
return path # a FileNotFoundError will be raised on a first read attempt
|
||||
if len(matches) == 1:
|
||||
return matches[0]
|
||||
raise ValueError("Expected glob to expand to a single path, got %r" % (matches,))
|
||||
>>>>>>> upstream/3.1.0
|
||||
|
@ -187,7 +187,8 @@ def fantest(
|
||||
elif fan_type == "arduino":
|
||||
if not arduino_serial_url:
|
||||
arduino_serial_url = click.prompt(
|
||||
"\n%s\nArduino Serial url" % HELP_ARDUINO_SERIAL_URL, type=str
|
||||
"\n%s\nArduino Serial url" % HELP_ARDUINO_SERIAL_URL,
|
||||
type=str, # type: ignore
|
||||
)
|
||||
|
||||
# typeshed currently specifies `Optional[str]` for `default`,
|
||||
@ -197,17 +198,19 @@ def fantest(
|
||||
# Hence the `type: ignore`.
|
||||
arduino_baudrate = click.prompt( # type: ignore
|
||||
"\n%s\nBaudrate" % HELP_ARDUINO_BAUDRATE,
|
||||
type=int,
|
||||
type=int, # type: ignore
|
||||
default=str(arduino_baudrate),
|
||||
show_default=True,
|
||||
)
|
||||
if not arduino_pwm_pin and arduino_pwm_pin != 0:
|
||||
arduino_pwm_pin = click.prompt(
|
||||
"\n%s\nArduino PWM pin" % HELP_ARDUINO_PWM_PIN, type=int
|
||||
"\n%s\nArduino PWM pin" % HELP_ARDUINO_PWM_PIN,
|
||||
type=int, # type: ignore
|
||||
)
|
||||
if not arduino_tacho_pin and arduino_tacho_pin != 0:
|
||||
arduino_tacho_pin = click.prompt(
|
||||
"\n%s\nArduino Tachometer pin" % HELP_ARDUINO_TACHO_PIN, type=int
|
||||
"\n%s\nArduino Tachometer pin" % HELP_ARDUINO_TACHO_PIN,
|
||||
type=int, # type: ignore
|
||||
)
|
||||
|
||||
assert arduino_serial_url is not None
|
||||
|
@ -1,11 +1,13 @@
|
||||
import abc
|
||||
from typing import NewType, Type
|
||||
from typing import NewType, Tuple, Type
|
||||
|
||||
PWMValue = NewType("PWMValue", int) # [0..255]
|
||||
FanValue = NewType("FanValue", int)
|
||||
|
||||
|
||||
class _SlotsReprMixin:
|
||||
__slots__: Tuple[str, ...]
|
||||
|
||||
def __eq__(self, other):
|
||||
if isinstance(other, type(self)):
|
||||
for attr in self.__slots__:
|
||||
|
@ -1,7 +1,11 @@
|
||||
from pathlib import Path
|
||||
from typing import NewType
|
||||
|
||||
<<<<<<< HEAD
|
||||
from afancontrol.configparser import ConfigParserSection
|
||||
=======
|
||||
from afancontrol.configparser import ConfigParserSection, expand_glob
|
||||
>>>>>>> upstream/3.1.0
|
||||
from afancontrol.pwmfan.base import (
|
||||
BaseFanPWMRead,
|
||||
BaseFanPWMWrite,
|
||||
@ -18,7 +22,11 @@ class LinuxFanSpeed(BaseFanSpeed):
|
||||
__slots__ = ("_fan_input",)
|
||||
|
||||
def __init__(self, fan_input: FanInputDevice) -> None:
|
||||
self._fan_input = Path(fan_input)
|
||||
self._fan_input = Path(expand_glob(fan_input))
|
||||
|
||||
@classmethod
|
||||
def from_configparser(cls, section: ConfigParserSection) -> BaseFanSpeed:
|
||||
return cls(FanInputDevice(section["fan_input"]))
|
||||
|
||||
@classmethod
|
||||
def from_configparser(cls, section: ConfigParserSection) -> BaseFanSpeed:
|
||||
@ -35,7 +43,11 @@ class LinuxFanPWMRead(BaseFanPWMRead):
|
||||
min_pwm = PWMValue(0)
|
||||
|
||||
def __init__(self, pwm: PWMDevice) -> None:
|
||||
self._pwm = Path(pwm)
|
||||
self._pwm = Path(expand_glob(pwm))
|
||||
|
||||
@classmethod
|
||||
def from_configparser(cls, section: ConfigParserSection) -> BaseFanPWMRead:
|
||||
return cls(PWMDevice(section["pwm"]))
|
||||
|
||||
@classmethod
|
||||
def from_configparser(cls, section: ConfigParserSection) -> BaseFanPWMRead:
|
||||
@ -51,8 +63,13 @@ class LinuxFanPWMWrite(BaseFanPWMWrite):
|
||||
read_cls = LinuxFanPWMRead
|
||||
|
||||
def __init__(self, pwm: PWMDevice) -> None:
|
||||
self._pwm = Path(pwm)
|
||||
self._pwm_enable = Path(pwm + "_enable")
|
||||
base = expand_glob(pwm)
|
||||
self._pwm = Path(base)
|
||||
self._pwm_enable = Path(base + "_enable")
|
||||
|
||||
@classmethod
|
||||
def from_configparser(cls, section: ConfigParserSection) -> BaseFanPWMWrite:
|
||||
return cls(PWMDevice(section["pwm"]))
|
||||
|
||||
@classmethod
|
||||
def from_configparser(cls, section: ConfigParserSection) -> BaseFanPWMWrite:
|
||||
|
@ -1,21 +1,15 @@
|
||||
import glob
|
||||
import re
|
||||
from pathlib import Path
|
||||
from typing import Optional, Tuple
|
||||
|
||||
<<<<<<< HEAD
|
||||
from afancontrol.configparser import ConfigParserSection
|
||||
=======
|
||||
from afancontrol.configparser import ConfigParserSection, expand_glob
|
||||
>>>>>>> upstream/3.1.0
|
||||
from afancontrol.temp.base import Temp, TempCelsius
|
||||
|
||||
|
||||
def _expand_glob(path: str):
|
||||
matches = glob.glob(path)
|
||||
if not matches:
|
||||
return path # a FileNotFoundError will be raised on a first read attempt
|
||||
if len(matches) == 1:
|
||||
return matches[0]
|
||||
raise ValueError("Expected glob to expand to a single path, got %r" % (matches,))
|
||||
|
||||
|
||||
class FileTemp(Temp):
|
||||
def __init__(
|
||||
self,
|
||||
@ -33,7 +27,7 @@ class FileTemp(Temp):
|
||||
# /sys/devices/pci0000:00/0000:00:01.3/[...]/hwmon/hwmon*/temp1_input
|
||||
# The `hwmon*` might change after reboot, but it is always a single
|
||||
# directory within the device.
|
||||
temp_path = _expand_glob(temp_path + "_input")
|
||||
temp_path = expand_glob(temp_path + "_input")
|
||||
temp_path = re.sub(r"_input$", "", temp_path)
|
||||
|
||||
self._temp_input = Path(temp_path + "_input")
|
||||
|
@ -6,7 +6,8 @@ import pytest
|
||||
from click.testing import CliRunner
|
||||
|
||||
from afancontrol import daemon
|
||||
from afancontrol.daemon import PidFile, Signals, daemon as main
|
||||
from afancontrol.daemon import PidFile, Signals
|
||||
from afancontrol.daemon import daemon as main
|
||||
|
||||
|
||||
def test_main_smoke(temp_path):
|
||||
|
@ -10,9 +10,9 @@ from afancontrol.fantest import (
|
||||
CSVMeasurementsOutput,
|
||||
HumanMeasurementsOutput,
|
||||
MeasurementsOutput,
|
||||
fantest as main,
|
||||
run_fantest,
|
||||
)
|
||||
from afancontrol.fantest import fantest as main
|
||||
from afancontrol.fantest import run_fantest
|
||||
from afancontrol.pwmfan import (
|
||||
BaseFanPWMRead,
|
||||
BaseFanPWMWrite,
|
||||
|
13
tox.ini
13
tox.ini
@ -1,5 +1,9 @@
|
||||
[tox]
|
||||
<<<<<<< HEAD
|
||||
envlist=py{36,37,38,39,310}{,-arduino,-metrics},lint,check-docs
|
||||
=======
|
||||
envlist=py{37,38,39,310,311,312}{,-arduino,-metrics},lint,check-docs
|
||||
>>>>>>> upstream/3.1.0
|
||||
|
||||
[testenv]
|
||||
extras =
|
||||
@ -12,6 +16,15 @@ commands = make test
|
||||
; sources to the working dir by default.
|
||||
usedevelop = True
|
||||
|
||||
[gh-actions]
|
||||
python =
|
||||
3.7: py37
|
||||
3.8: py38
|
||||
3.9: py39
|
||||
3.10: py310
|
||||
3.11: py311
|
||||
3.12: py312
|
||||
|
||||
[testenv:lint]
|
||||
extras =
|
||||
arduino
|
||||
|
Loading…
Reference in New Issue
Block a user