]> arthur.barton.de Git - netdata.git/blobdiff - plugins.d/python.d.plugin
preserve configs across installaitons
[netdata.git] / plugins.d / python.d.plugin
index 5e928b3f4e62d97c284998d5bcb22ed840d07153..5dc4f0b0612e2f16edbae4e97c19c5dd32b93418 100755 (executable)
@@ -22,44 +22,23 @@ class PythonCharts(object):
                  modules_configs='../conf.d/',
                  modules_disabled=[]):
         self.first_run = True
-        if interval is None:
-            interval = 1
         self.default_priority = 90000
-        # check if plugin directory exists
-        if not os.path.isdir(modules_path):
-            debug("cannot find charts directory ", modules_path)
-            sys.stdout.write("DISABLE\n")
-            sys.exit(1)
         # set configuration directory
         self.configs = modules_configs
 
         # load modules
-        self.modules = []
-        if len(modules) > 0:
-            for m in modules:
-                mod = self.import_plugin(modules_path + m + ".chart.py")
-                if mod is not None:
-                    self.modules.append(mod)
-        else:
-            self.autoload_modules(modules_path)
+        modules = self._load_modules(modules_path,modules)
         
-        # check if there are any modules loaded
-        if len(self.modules) == 0:
-            debug("cannot find modules", modules_path)
-            sys.stdout.write("DISABLE\n")
-            sys.exit(1)
-
-        # check if loaded modules is on disabled modules list
-        for mod in self.modules:
-            if mod.__name__ in modules_disabled:
-                self.modules.remove(mod)
+        # check if loaded modules are on disabled modules list
+        self.modules = [ m for m in modules if m.__name__ not in modules_disabled ]
         
         # load configuration files
-        self.load_configs()
+        self._load_configs()
 
         # set timetable dict (last execution, next execution and frequency)
         # set priorities
         self.timetable = {}
+        freq = 1
         for m in self.modules:
             try:
                 m.priority = int(m.priority)
@@ -68,16 +47,16 @@ class PythonCharts(object):
              
             if interval is None:
                 try:
-                    interval = int(m.update_every)
+                    freq = int(m.update_every)
                 except (AttributeError, ValueError):
-                    interval = 1
+                    freq = 1
             
             now = time.time()
             self.timetable[m.__name__] = {'last' : now,
-                                          'next' : now - (now % interval) + interval,
-                                          'freq' : interval}
+                                          'next' : now - (now % freq) + freq,
+                                          'freq' : freq}
 
-    def import_plugin(self, path, name=None):
+    def _import_plugin(self, path, name=None):
     # try to import module using only its path
         if name is None:
             name = path.split('/')[-1]
@@ -90,17 +69,31 @@ class PythonCharts(object):
             debug(str(e))
             return None
 
-    def autoload_modules(self, path):
-    # scan directory specified in path and load all modules from there
-    # function modifies self.modules
-        names = os.listdir(path)
-        for mod in names:
-            m = self.import_plugin(path + mod)
-            if m is not None:
-                debug("loading chart: '" + path + mod + "'")
-                self.modules.append(m)
+    def _load_modules(self, path, modules):
+        # check if plugin directory exists
+        if not os.path.isdir(path):
+            debug("cannot find charts directory ", path)
+            sys.stdout.write("DISABLE\n")
+            sys.exit(1)
 
-    def load_configs(self):
+        # load modules
+        loaded = []
+        if len(modules) > 0:
+            for m in modules:
+                mod = self._import_plugin(path + m + ".chart.py")
+                if mod is not None:
+                    loaded.append(mod)
+        else:
+            # scan directory specified in path and load all modules from there
+            names = os.listdir(path)
+            for mod in names:
+                m = self._import_plugin(path + mod)
+                if m is not None:
+                    debug("loading chart: '" + path + mod + "'")
+                    loaded.append(m)
+        return loaded
+
+    def _load_configs(self):
     # function modifies every loaded module in self.modules
         for m in self.modules:
             configfile = self.configs + m.__name__ + ".conf"
@@ -114,7 +107,7 @@ class PythonCharts(object):
                       configfile +
                       "' not found. Using defaults.")
 
-    def disable_module(self, mod, reason=None):
+    def _disable_module(self, mod, reason=None):
     # modifies self.modules
         self.modules.remove(mod)
         del self.timetable[mod.__name__]
@@ -128,9 +121,9 @@ class PythonCharts(object):
                   "() function. Disabling it.")
         elif reason[:7] == "failed ":
             debug("chart '" +
-                  mod.__name__ +
-                  reason[3:] +
-                  "() function. reports failure.")
+                  mod.__name__ + "' " +
+                  reason[7:] +
+                  "() function reports failure.")
         elif reason[:13] == "configuration":
             debug(mod.__name__,
                   "configuration file '" +
@@ -145,18 +138,18 @@ class PythonCharts(object):
         for mod in self.modules:
             try:
                 if not mod.check():
-                    self.disable_module(mod, "failed check")
+                    self._disable_module(mod, "failed check")
             except AttributeError:
-                self.disable_module(mod, "no check")
+                self._disable_module(mod, "no check")
             except (UnboundLocalError, Exception) as e:
-                self.disable_module(mod, "misbehaving. Reason: " + str(e))
+                self._disable_module(mod, "misbehaving. Reason: " + str(e))
 
     def create(self):
     # try to execute create() on every loaded module
         for mod in self.modules:
             try:
                 if not mod.create():
-                    self.disable_module(mod, "failed create")
+                    self._disable_module(mod, "failed create")
                 else:
                     chart = mod.__name__
                     sys.stdout.write(
@@ -170,11 +163,11 @@ class PythonCharts(object):
                     sys.stdout.write("DIMENSION run_time 'run time' absolute 1 1\n\n")
                     sys.stdout.flush()
             except AttributeError:
-                self.disable_module(mod, "no create")
+                self._disable_module(mod, "no create")
             except (UnboundLocalError, Exception) as e:
-                self.disable_module(mod, "misbehaving. Reason: " + str(e))
+                self._disable_module(mod, "misbehaving. Reason: " + str(e))
 
-    def update_module(self, mod):
+    def _update_module(self, mod):
     # try to execute update() on every module and draw run time graph 
         t_start = time.time()
         # check if it is time to execute module update() function
@@ -186,13 +179,13 @@ class PythonCharts(object):
             else:
                 since_last = int((t_start - self.timetable[mod.__name__]['last']) * 1000000)
             if not mod.update(since_last):
-                self.disable_module(mod, "update failed")
+                self._disable_module(mod, "update failed")
                 return
         except AttributeError:
-            self.disable_module(mod, "no update")
+            self._disable_module(mod, "no update")
             return
         except (UnboundLocalError, Exception) as e:
-            self.disable_module(mod, "misbehaving. Reason: " + str(e))
+            self._disable_module(mod, "misbehaving. Reason: " + str(e))
             return
         t_end = time.time()
         self.timetable[mod.__name__]['next'] = t_end - (t_end % self.timetable[mod.__name__]['freq']) + self.timetable[mod.__name__]['freq']
@@ -215,7 +208,7 @@ class PythonCharts(object):
             t_begin = time.time()
             next_runs = []
             for mod in self.modules:
-                self.update_module(mod)
+                self._update_module(mod)
                 try:
                     next_runs.append(self.timetable[mod.__name__]['next'])
                 except KeyError:
@@ -277,6 +270,8 @@ def parse_cmdline(directory, *commands):
                 pass
 
     debug("started from", commands[0], "with options:", *commands[1:])
+    if len(mods) == 0 and DEBUG_FLAG is False:
+        interval = None
 
     return {'interval': interval,
             'modules': mods}
@@ -292,14 +287,13 @@ def run():
     main_dir = os.getenv('NETDATA_PLUGINS_DIR',
                          os.path.abspath(__file__).strip("python.d.plugin.py"))
     config_dir = os.getenv('NETDATA_CONFIG_DIR', "/etc/netdata/")
-    interval = int(os.getenv('NETDATA_UPDATE_EVERY', 1))
+    interval = os.getenv('NETDATA_UPDATE_EVERY', None)
 
     # read configuration file
     disabled = []
     if config_dir[-1] != '/':
-        configfile = config_dir + '/' + "python.d.conf"
-    else:
-        configfile = config_dir + "python.d.conf"
+        config_dir += '/'
+    configfile = config_dir + "python.d.conf"
 
     try:
         conf = read_config(configfile)
@@ -313,7 +307,7 @@ def run():
         try:
             modules_conf = conf['plugins_config_dir']
         except (KeyError):
-            modules_conf = config_dir  # default configuration directory
+            modules_conf = config_dir + "python.d/"  # default configuration directory
         try:
             modules_dir = conf['plugins_dir']
         except (KeyError):
@@ -326,10 +320,11 @@ def run():
             DEBUG_FLAG = bool(conf['debug'])
         except (KeyError, TypeError):
             pass
-        try:
-            disabled = conf['disabled'].split(',')
-        except (KeyError):
-            pass
+        for k, v in conf.items():
+            if k in ("plugins_config_dir", "plugins_dir", "interval", "debug"):
+                continue
+            if v == 'no':
+                disabled.append(k)
     except FileNotFoundError:
         modules_conf = config_dir
         modules_dir = main_dir.replace("plugins.d", "python.d")
@@ -345,7 +340,7 @@ def run():
     modules = out['modules']
     if out['interval'] is not None:
         interval = out['interval']
-
+    
     # configure environement to run modules
     sys.path.append(modules_dir+"python_modules") # append path to directory with modules dependencies