From f37913e898441be3b86180daf329cb40f362f2f3 Mon Sep 17 00:00:00 2001 From: Michael Tremer Date: Wed, 27 May 2015 15:46:20 +0000 Subject: [PATCH] Migrate to Python 3 --- configure.ac | 2 +- src/_collectymodule.c | 47 +++++++++++++++++--------- src/collecty/__init__.py | 8 ++--- src/collecty/bus.py | 27 +++++++++------ src/collecty/client.py | 8 ++--- src/collecty/constants.py | 4 +-- src/collecty/daemon.py | 27 +++++++++------ src/collecty/errors.py | 2 +- src/collecty/i18n.py | 2 +- src/collecty/logger.py | 2 +- src/collecty/ping.py | 16 ++++----- src/collecty/plugins/__init__.py | 26 +++++++------- src/collecty/plugins/base.py | 56 +++++++++++++++---------------- src/collecty/plugins/conntrack.py | 6 ++-- src/collecty/plugins/cpu.py | 6 ++-- src/collecty/plugins/cpufreq.py | 4 +-- src/collecty/plugins/disk.py | 4 +-- src/collecty/plugins/entropy.py | 4 +-- src/collecty/plugins/interface.py | 6 ++-- src/collecty/plugins/latency.py | 6 ++-- src/collecty/plugins/loadavg.py | 4 +-- src/collecty/plugins/memory.py | 6 ++-- src/collecty/plugins/sensors.py | 4 +-- 23 files changed, 149 insertions(+), 128 deletions(-) diff --git a/configure.ac b/configure.ac index ab73027..46fc55b 100644 --- a/configure.ac +++ b/configure.ac @@ -62,7 +62,7 @@ AC_PROG_GCC_TRADITIONAL AC_PATH_PROG([XSLTPROC], [xsltproc]) # Python -AM_PATH_PYTHON([2.7]) +AM_PATH_PYTHON([3.2]) PKG_CHECK_MODULES([PYTHON], [python-${PYTHON_VERSION}]) # libatasmart diff --git a/src/_collectymodule.c b/src/_collectymodule.c index e57970e..422c27d 100644 --- a/src/_collectymodule.c +++ b/src/_collectymodule.c @@ -45,7 +45,7 @@ static void BlockDevice_dealloc(BlockDevice* self) { if (self->path) free(self->path); - self->ob_type->tp_free((PyObject*)self); + Py_TYPE(self)->tp_free((PyObject*)self); } static int BlockDevice_get_identity(BlockDevice* device) { @@ -143,7 +143,7 @@ static int BlockDevice_init(BlockDevice* self, PyObject* args, PyObject* kwds) { static PyObject* BlockDevice_get_path(PyObject* self) { BlockDevice* device = (BlockDevice*)self; - return PyString_FromString(device->path); + return PyUnicode_FromString(device->path); } static void clean_string(char *s) { @@ -195,7 +195,7 @@ static PyObject* BlockDevice_get_model(PyObject* self) { char model[MODEL_SIZE + 1]; copy_string(model, device->identity.model, sizeof(model)); - return PyString_FromString(model); + return PyUnicode_FromString(model); } static PyObject* BlockDevice_get_serial(PyObject* self) { @@ -204,7 +204,7 @@ static PyObject* BlockDevice_get_serial(PyObject* self) { char serial[SERIAL_SIZE + 1]; copy_string(serial, device->identity.serial_no, sizeof(serial)); - return PyString_FromString(serial); + return PyUnicode_FromString(serial); } static PyObject* BlockDevice_is_smart_supported(PyObject* self) { @@ -273,8 +273,7 @@ static PyMethodDef BlockDevice_methods[] = { }; static PyTypeObject BlockDeviceType = { - PyObject_HEAD_INIT(NULL) - 0, /*ob_size*/ + PyVarObject_HEAD_INIT(NULL, 0) "_collecty.BlockDevice", /*tp_name*/ sizeof(BlockDevice), /*tp_basicsize*/ 0, /*tp_itemsize*/ @@ -321,7 +320,7 @@ typedef struct { } SensorObject; static void Sensor_dealloc(SensorObject* self) { - self->ob_type->tp_free((PyObject*)self); + Py_TYPE(self)->tp_free((PyObject*)self); } static PyObject* Sensor_new(PyTypeObject* type, PyObject* args, PyObject* kwds) { @@ -338,7 +337,7 @@ static PyObject* Sensor_get_label(SensorObject* self) { char* label = sensors_get_label(self->chip, self->feature); if (label) { - PyObject* string = PyString_FromString(label); + PyObject* string = PyUnicode_FromString(label); free(label); return string; @@ -356,7 +355,7 @@ static PyObject* Sensor_get_name(SensorObject* self) { return NULL; } - return PyString_FromString(chip_name); + return PyUnicode_FromString(chip_name); } static PyObject* Sensor_get_type(SensorObject* self) { @@ -384,7 +383,7 @@ static PyObject* Sensor_get_type(SensorObject* self) { } if (type) - return PyString_FromString(type); + return PyUnicode_FromString(type); Py_RETURN_NONE; } @@ -426,7 +425,7 @@ static PyObject* Sensor_get_bus(SensorObject* self) { } if (type) - return PyString_FromString(type); + return PyUnicode_FromString(type); Py_RETURN_NONE; } @@ -602,7 +601,6 @@ static PyGetSetDef Sensor_getsetters[] = { static PyTypeObject SensorType = { PyObject_HEAD_INIT(NULL) - 0, /*ob_size*/ "_collecty.Sensor", /*tp_name*/ sizeof(SensorObject), /*tp_basicsize*/ 0, /*tp_itemsize*/ @@ -729,15 +727,32 @@ static PyMethodDef collecty_module_methods[] = { {NULL}, }; -void init_collecty(void) { +static struct PyModuleDef collecty_module = { + PyModuleDef_HEAD_INIT, + "_collecty", /* m_name */ + "_collecty module", /* m_doc */ + -1, /* m_size */ + collecty_module_methods, /* m_methods */ + NULL, /* m_reload */ + NULL, /* m_traverse */ + NULL, /* m_clear */ + NULL, /* m_free */ +}; + +PyMODINIT_FUNC PyInit__collecty(void) { if (PyType_Ready(&BlockDeviceType) < 0) - return; + return NULL; if (PyType_Ready(&SensorType) < 0) - return; + return NULL; - PyObject* m = Py_InitModule("_collecty", collecty_module_methods); + PyObject* m = PyModule_Create(&collecty_module); + Py_INCREF(&BlockDeviceType); PyModule_AddObject(m, "BlockDevice", (PyObject*)&BlockDeviceType); + + Py_INCREF(&SensorType); PyModule_AddObject(m, "Sensor", (PyObject*)&SensorType); + + return m; } diff --git a/src/collecty/__init__.py b/src/collecty/__init__.py index ab16c12..a1a60f0 100644 --- a/src/collecty/__init__.py +++ b/src/collecty/__init__.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -20,7 +20,7 @@ ############################################################################### # Initialize logging. -import logger +from . import logger -from client import CollectyClient -from daemon import Collecty +from .client import CollectyClient +from .daemon import Collecty diff --git a/src/collecty/bus.py b/src/collecty/bus.py index 6a3f0bd..d67332f 100644 --- a/src/collecty/bus.py +++ b/src/collecty/bus.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -22,20 +22,17 @@ import dbus import dbus.mainloop.glib import dbus.service -import gobject +import gi.repository.GLib +import gi.repository.GObject import threading -from constants import * -from i18n import _ +from .constants import * +from .i18n import _ import logging log = logging.getLogger("collecty.bus") log.propagate = 1 -# Initialise the glib main loop -dbus.mainloop.glib.DBusGMainLoop(set_as_default=True) -dbus.mainloop.glib.threads_init() - class Bus(threading.Thread): def __init__(self, collecty): threading.Thread.__init__(self) @@ -44,8 +41,11 @@ class Bus(threading.Thread): self.collecty = collecty # Initialise the main loop - gobject.threads_init() - self.loop = gobject.MainLoop() + gi.repository.GObject.threads_init() + dbus.mainloop.glib.threads_init() + dbus.mainloop.glib.DBusGMainLoop(set_as_default=True) + + self.loop = gi.repository.GLib.MainLoop() # Register the GraphGenerator interface self.generator = GraphGenerator(self.collecty) @@ -54,7 +54,12 @@ class Bus(threading.Thread): log.debug(_("Bus thread has started")) # Run the main loop - self.loop.run() + try: + self.loop.run() + except KeyboardInterrupt: + self.collecty.shutdown() + + log.debug(_("Bus thread has ended")) def shutdown(self): log.debug(_("Stopping bus thread")) diff --git a/src/collecty/client.py b/src/collecty/client.py index 1f07225..0e870a2 100644 --- a/src/collecty/client.py +++ b/src/collecty/client.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -23,8 +23,8 @@ import argparse import dbus import sys -from constants import * -from i18n import _ +from .constants import * +from .i18n import _ import logging log = logging.getLogger("collectly.client") @@ -44,7 +44,7 @@ class CollectyClient(object): templates = self.list_templates() for t in sorted(templates): - print t + print(t) def generate_graph(self, template_name, **kwargs): byte_array = self.proxy.GenerateGraph(template_name, kwargs, diff --git a/src/collecty/constants.py b/src/collecty/constants.py index 8580d14..34d5406 100644 --- a/src/collecty/constants.py +++ b/src/collecty/constants.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -19,7 +19,7 @@ # # ############################################################################### -from i18n import _ +from .i18n import _ DATABASE_DIR = "/var/lib/collecty" diff --git a/src/collecty/daemon.py b/src/collecty/daemon.py index bb46971..167d000 100644 --- a/src/collecty/daemon.py +++ b/src/collecty/daemon.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -19,19 +19,19 @@ # # ############################################################################### -import Queue as queue import datetime import multiprocessing +import queue import rrdtool import signal import threading import time -import bus -import plugins +from . import bus +from . import plugins -from constants import * -from i18n import _ +from .constants import * +from .i18n import _ import logging log = logging.getLogger("collecty") @@ -96,6 +96,11 @@ class Collecty(object): # Register signal handlers. self.register_signal_handler() + # Cannot do anything if no plugins have been initialised + if not self.plugins: + log.critical(_("No plugins have been initialised")) + return + # Start the bus self.bus.start() @@ -335,7 +340,7 @@ class WriteQueue(threading.Thread): results[result.file] = [result] # Write the collected data to disk - for filename, results in results.items(): + for filename, results in list(results.items()): self._commit_file(filename, results) duration = time.time() - time_start @@ -367,8 +372,8 @@ class QueueObject(object): def __str__(self): return "%s:%s" % (self.time.strftime("%s"), self.data) - def __cmp__(self, other): - return cmp(self.time, other.time) + def __lt__(self, other): + return self.time < other.time class PluginTimer(object): @@ -380,8 +385,8 @@ class PluginTimer(object): def __repr__(self): return "<%s %s>" % (self.__class__.__name__, self.deadline) - def __cmp__(self, other): - return cmp(self.deadline, other.deadline) + def __lt__(self, other): + return self.deadline < other.deadline def reset_deadline(self): self.deadline = datetime.datetime.utcnow() \ diff --git a/src/collecty/errors.py b/src/collecty/errors.py index 0dbe485..dacacb1 100644 --- a/src/collecty/errors.py +++ b/src/collecty/errors.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # diff --git a/src/collecty/i18n.py b/src/collecty/i18n.py index 75c78fe..a7c3701 100644 --- a/src/collecty/i18n.py +++ b/src/collecty/i18n.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # diff --git a/src/collecty/logger.py b/src/collecty/logger.py index f1c732c..e23af19 100644 --- a/src/collecty/logger.py +++ b/src/collecty/logger.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # diff --git a/src/collecty/ping.py b/src/collecty/ping.py index 60b5537..e2d7970 100644 --- a/src/collecty/ping.py +++ b/src/collecty/ping.py @@ -1,6 +1,4 @@ -#!/usr/bin/python - -from __future__ import division +#!/usr/bin/python3 import array import math @@ -118,8 +116,8 @@ class Ping(object): # Send the packet. try: s.sendto(packet, (self.destination, 0)) - except socket.error, (errno, msg): - if errno == 1: # Operation not permitted + except socket.error as e: + if e.errno == 1: # Operation not permitted # The packet could not be sent, probably because of # wrong firewall settings. return @@ -175,7 +173,7 @@ class Ping(object): Unpack tghe raw received IP and ICMP header informations to a dict """ unpacked_data = struct.unpack(struct_format, data) - return dict(zip(names, unpacked_data)) + return dict(list(zip(names, unpacked_data))) def _calculate_checksum(self, source_string): if len(source_string) % 2: @@ -321,6 +319,6 @@ if __name__ == "__main__": p = Ping("ping.ipfire.org") p.run(count=5) - print "Min/Avg/Max/Stddev: %.2f/%.2f/%.2f/%.2f" % \ - (p.min_time, p.avg_time, p.max_time, p.stddev) - print "Sent/Recv/Loss: %d/%d/%.2f" % (p.send_count, p.receive_count, p.loss) + print("Min/Avg/Max/Stddev: %.2f/%.2f/%.2f/%.2f" % \ + (p.min_time, p.avg_time, p.max_time, p.stddev)) + print("Sent/Recv/Loss: %d/%d/%.2f" % (p.send_count, p.receive_count, p.loss)) diff --git a/src/collecty/plugins/__init__.py b/src/collecty/plugins/__init__.py index b68acc9..3e92bf6 100644 --- a/src/collecty/plugins/__init__.py +++ b/src/collecty/plugins/__init__.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -19,16 +19,16 @@ # # ############################################################################### -from base import Timer, get +from .base import Timer, get -import base -import conntrack -import cpu -import cpufreq -import disk -import entropy -import interface -import latency -import loadavg -import memory -import sensors +from . import base +from . import conntrack +from . import cpu +from . import cpufreq +from . import disk +from . import entropy +from . import interface +from . import latency +from . import loadavg +from . import memory +from . import sensors diff --git a/src/collecty/plugins/base.py b/src/collecty/plugins/base.py index 8d768ae..048ebcb 100644 --- a/src/collecty/plugins/base.py +++ b/src/collecty/plugins/base.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -19,8 +19,6 @@ # # ############################################################################### -from __future__ import division - import datetime import logging import math @@ -29,18 +27,11 @@ import rrdtool import tempfile import threading import time +import unicodedata from ..constants import * from ..i18n import _ -_plugins = {} - -def get(): - """ - Returns a list with all automatically registered plugins. - """ - return _plugins.values() - class Timer(object): def __init__(self, timeout, heartbeat=1): self.timeout = timeout @@ -73,7 +64,30 @@ class Timer(object): return self.elapsed > self.timeout -class Plugin(object): +class PluginRegistration(type): + plugins = {} + + def __init__(plugin, name, bases, dict): + type.__init__(plugin, name, bases, dict) + + # The main class from which is inherited is not registered + # as a plugin. + if name == "Plugin": + return + + if not all((plugin.name, plugin.description)): + raise RuntimeError(_("Plugin is not properly configured: %s") % plugin) + + PluginRegistration.plugins[plugin.name] = plugin + + +def get(): + """ + Returns a list with all automatically registered plugins. + """ + return PluginRegistration.plugins.values() + +class Plugin(object, metaclass=PluginRegistration): # The name of this plugin. name = None @@ -87,22 +101,6 @@ class Plugin(object): # The default interval for all plugins interval = 60 - # Automatically register all providers. - class __metaclass__(type): - def __init__(plugin, name, bases, dict): - type.__init__(plugin, name, bases, dict) - - # The main class from which is inherited is not registered - # as a plugin. - if name == "Plugin": - return - - if not all((plugin.name, plugin.description)): - raise RuntimeError(_("Plugin is not properly configured: %s") \ - % plugin) - - _plugins[plugin.name] = plugin - def __init__(self, collecty, **kwargs): self.collecty = collecty @@ -254,7 +252,7 @@ class Object(object): @staticmethod def _normalise_filename(filename): # Convert the filename into ASCII characters only - filename = filename.encode("ascii", "ignore") + filename = unicodedata.normalize("NFKC", filename) # Replace any spaces by dashes filename = filename.replace(" ", "-") diff --git a/src/collecty/plugins/conntrack.py b/src/collecty/plugins/conntrack.py index 0e1c6d9..82f9e6a 100644 --- a/src/collecty/plugins/conntrack.py +++ b/src/collecty/plugins/conntrack.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -21,7 +21,7 @@ import os -import base +from . import base from ..i18n import _ @@ -117,7 +117,7 @@ class ConntrackTable(object): layer4_protocol = "other" # Count connection states - if self.protocol_states.has_key(layer4_protocol): + if layer4_protocol in self.protocol_states: state = line[5] try: diff --git a/src/collecty/plugins/cpu.py b/src/collecty/plugins/cpu.py index 962163f..09d5051 100644 --- a/src/collecty/plugins/cpu.py +++ b/src/collecty/plugins/cpu.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -19,9 +19,9 @@ # # ############################################################################### -from __future__ import division -import base + +from . import base from ..i18n import _ diff --git a/src/collecty/plugins/cpufreq.py b/src/collecty/plugins/cpufreq.py index 7deeae6..19f099a 100644 --- a/src/collecty/plugins/cpufreq.py +++ b/src/collecty/plugins/cpufreq.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -22,7 +22,7 @@ import os import re -import base +from . import base from ..i18n import _ diff --git a/src/collecty/plugins/disk.py b/src/collecty/plugins/disk.py index b0f40a2..f274085 100644 --- a/src/collecty/plugins/disk.py +++ b/src/collecty/plugins/disk.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -23,7 +23,7 @@ from collecty import _collecty import os import re -import base +from . import base from ..i18n import _ diff --git a/src/collecty/plugins/entropy.py b/src/collecty/plugins/entropy.py index e6e920d..0b3fa5a 100644 --- a/src/collecty/plugins/entropy.py +++ b/src/collecty/plugins/entropy.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -21,7 +21,7 @@ import os -import base +from . import base from ..i18n import _ diff --git a/src/collecty/plugins/interface.py b/src/collecty/plugins/interface.py index addca19..eeb8be6 100644 --- a/src/collecty/plugins/interface.py +++ b/src/collecty/plugins/interface.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -19,11 +19,11 @@ # # ############################################################################### -from __future__ import division + import os -import base +from . import base from ..i18n import _ diff --git a/src/collecty/plugins/latency.py b/src/collecty/plugins/latency.py index 0b2324a..007262c 100644 --- a/src/collecty/plugins/latency.py +++ b/src/collecty/plugins/latency.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -21,7 +21,7 @@ import collecty.ping -import base +from . import base from ..i18n import _ @@ -107,7 +107,7 @@ class LatencyObject(base.Object): ping = collecty.ping.Ping(destination=self.hostname, timeout=20000) ping.run(count=5, deadline=self.deadline) - except collecty.ping.PingError, e: + except collecty.ping.PingError as e: self.log.warning(_("Could not run latency check for %(host)s: %(msg)s") \ % { "host" : self.hostname, "msg" : e.msg }) return diff --git a/src/collecty/plugins/loadavg.py b/src/collecty/plugins/loadavg.py index 24cce74..090c9f4 100644 --- a/src/collecty/plugins/loadavg.py +++ b/src/collecty/plugins/loadavg.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -21,7 +21,7 @@ import os -import base +from . import base from ..i18n import _ diff --git a/src/collecty/plugins/memory.py b/src/collecty/plugins/memory.py index 55d6586..3310f71 100644 --- a/src/collecty/plugins/memory.py +++ b/src/collecty/plugins/memory.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 ############################################################################### # # # collecty - A system statistics collection daemon for IPFire # @@ -19,9 +19,9 @@ # # ############################################################################### -from __future__ import division -import base + +from . import base from ..i18n import _ diff --git a/src/collecty/plugins/sensors.py b/src/collecty/plugins/sensors.py index e4c247e..f3b3c25 100644 --- a/src/collecty/plugins/sensors.py +++ b/src/collecty/plugins/sensors.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python3 # encoding: utf-8 ############################################################################### # # @@ -24,7 +24,7 @@ from collecty import _collecty import os import re -import base +from . import base from ..i18n import _ -- 2.39.2