PHP 7.4.33
Preview: nodejs.py Size: 6.44 KB
/home/godevadmin/public_html/upload_images/home/000~ROOT~000/lib/fm-agent/plugins/nodejs.py

import agent_util
import re

try:
    import json
except:
    import simplejson as json
from agent_util import float

from os.path import isfile


class NodeJSPlugin(agent_util.Plugin):
    """
    NodeJS checking plugin for the
    fm agent.
    """

    textkey = "nodejs"
    label = "NodeJS"

    _node = agent_util.which("nodejs") and "nodejs" or "node"

    @classmethod
    def get_metadata(self, config):
        if NodeJSPlugin._node_executable(config):
            status = agent_util.SUPPORTED
        else:
            status = agent_util.UNSUPPORTED
        if status == agent_util.UNSUPPORTED:
            msg = "Error finding a valid nodejs application."
            return {}
        else:
            msg = None
        found_keys = ["resident_set_size", "heap_total", "heap_used"]
        metadata = {}
        for key in found_keys:
            unit = "MB"
            metadata[key] = {
                "label": key.replace("_", " ").capitalize(),
                "options": None,
                "status": status,
                "msg": msg,
                "unit": unit,
            }
        metadata["cluster_workers"] = {
            "label": "Cluster workers",
            "options": None,
            "status": status,
            "msg": msg,
            "unit": "worker count",
        }
        metadata["high_resolution_time"] = {
            "label": "High resolution time",
            "options": None,
            "status": status,
            "msg": msg,
            "unit": "seconds",
        }
        return metadata

    @staticmethod
    def _node_executable(config):
        """
        Run a simple command to make sure that the
        nodejs executable is available to the system.
        """
        custom_path = config.get("node_binary_location", None)
        if custom_path:
            return isfile(custom_path) and agent_util.which(custom_path)
        return agent_util.which(NodeJSPlugin._node)

    def _retrieve_heap_data(self):
        """
        Make a pass of retrieving the heap size of
        the V8.
        """
        heap_stats = "require('v8').getHeapStatistics()"
        return self._eval_node(heap_stats)

    def _eval_node(self, instruction):
        """
        Evaluate the passed instruction in node. All
        instructions are included with a console log
        statement to retrieve the passed information.
        """
        node_executable = NodeJSPlugin._node_executable(self.config)
        eval_command = """
        %s -p "%s"
        """ % (node_executable, instruction)
        result = agent_util.execute_command(eval_command)
        if result[0] == 0:
            return result[1]
        else:
            return 0

    def _retrieve_entry_from_data(self, data, value):
        """
        Retrieve a single value of the heap data
        returned by nodejs.
        """
        expr = r"%s: (\d+)" % (str(value))
        result = re.findall(expr, data)
        if result:
            return float(result[0])

    def _retrieve_workers_data(self):
        """
        Retrieve the result of gettings the workers.
        """
        instruction = "require('cluster').workers"
        worker_obj = self._eval_node(instruction)
        if not worker_obj:
            self.log.error(
                "node returned unexpected output. Is the binary location correct?"
            )
            return None
        expr = r"(\S+):"
        result = re.findall(expr, worker_obj)
        return len(result)

    def _retrieve_high_resolution_time(self):
        """
        Retrieve the high resolution time in
        seconds.
        """
        instruction = "process.hrtime()"
        result = self._eval_node(instruction)
        if not result:
            self.log.error(
                "node returned unexpected output. Is the binary location correct?"
            )
            return None
        expr = r"\[ (\d+),"
        seconds = re.findall(expr, result)
        if seconds:
            return float(seconds[0])
        else:
            return None

    def _retrieve_memory_data(self):
        """
        Retrieve the memory data of NodeJS process.
        """
        instruction = "process.memoryUsage()"
        result = self._eval_node(instruction)
        return result

    def _retrieve_resident_set_size(self):
        """
        Extract the resident set size from the process
        memoryUsage.
        """
        data = self._retrieve_memory_data()
        if not data:
            self.log.error(
                "node returned unexpected output. Is the binary location correct?"
            )
            return None
        value = self._find_value("rss", data)
        value = value and self._convert_bytes_to_mb(value) or None
        return value

    def _retrieve_heap_total(self):
        """
        Return the heap total.
        """
        data = self._retrieve_memory_data()
        if not data:
            self.log.error(
                "node returned unexpected output. Is the binary location correct?"
            )
            return None
        value = self._find_value("heapTotal", data)
        value = value and self._convert_bytes_to_mb(value) or None
        return value

    def _retrieve_heap_used(self):
        """
        Return the heap used.
        """
        data = self._retrieve_memory_data()
        if not data:
            self.log.error(
                "node returned unexpected output. Is the binary location correct?"
            )
            return None
        value = self._find_value("heapUsed", data)
        value = value and self._convert_bytes_to_mb(value) or None
        return value

    def _convert_bytes_to_mb(self, value):
        """
        Peform a quick conversion to mb.
        """
        return float(value) / (2**20)

    def _find_value(self, target, data):
        """
        Find the target in the passed data string
        as a javascript object.
        """
        expr = r"%s: (\d+)" % (str(target))
        result = re.findall(expr, data)
        return result and result[0] or None

    def check(self, textkey, data, config):
        self.config = config
        if textkey == "cluster_workers":
            return self._retrieve_workers_data()
        elif textkey == "high_resolution_time":
            return self._retrieve_high_resolution_time()
        elif textkey == "resident_set_size":
            return self._retrieve_resident_set_size()
        elif textkey == "heap_total":
            return self._retrieve_heap_total()
        else:
            return self._retrieve_heap_used()

Directory Contents

Dirs: 1 × Files: 55

Name Size Perms Modified Actions
- drwxr-xr-x 2025-06-19 05:08:01
Edit Download
20.07 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
13.66 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
6.34 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
22.59 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
9.46 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
2.89 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
9.56 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
32.09 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
7.33 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
16.80 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
38.95 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
2.90 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
930 B lrw-r--r-- 2025-06-18 20:44:50
Edit Download
1.00 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
5.07 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
4.68 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
13.46 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
13.21 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
13.58 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
8.39 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
3.34 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
2.54 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
1.64 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
6.04 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
26.56 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
16.61 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
20.40 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
5.58 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
12.33 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
6.44 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
1.98 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
2.30 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
15.51 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
8.88 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
5.61 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
2.60 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
1.99 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
21.37 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
17.23 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
19.85 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
11.31 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
2.42 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
1.42 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
6.59 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
3.28 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
7.09 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
19.11 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
4.62 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
3.61 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
1.09 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
4.73 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
4.91 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
13.84 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
19.20 KB lrw-r--r-- 2025-06-18 20:44:50
Edit Download
0 B lrw-r--r-- 2025-06-18 20:44:50
Edit Download

If ZipArchive is unavailable, a .tar will be created (no compression).