diff --git a/CHANGELOG.md b/CHANGELOG.md
index 40853ca113e39d..1539edf2e69146 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -2,10 +2,18 @@
## [**Next release**](https://github.com/netdata/netdata/tree/HEAD)
-[Full Changelog](https://github.com/netdata/netdata/compare/v1.46.2...HEAD)
+[Full Changelog](https://github.com/netdata/netdata/compare/v1.46.3...HEAD)
**Merged pull requests:**
+- go.d drop using cancelreader [\#18219](https://github.com/netdata/netdata/pull/18219) ([ilyam8](https://github.com/ilyam8))
+- Regenerate integrations.js [\#18216](https://github.com/netdata/netdata/pull/18216) ([netdatabot](https://github.com/netdatabot))
+- go.d chrony fix client read/write timeout [\#18215](https://github.com/netdata/netdata/pull/18215) ([ilyam8](https://github.com/ilyam8))
+- dont install test bash scripts by default [\#18214](https://github.com/netdata/netdata/pull/18214) ([ilyam8](https://github.com/ilyam8))
+- Regenerate integrations.js [\#18212](https://github.com/netdata/netdata/pull/18212) ([netdatabot](https://github.com/netdatabot))
+- go.d megacli: add bbu capacity degradation % [\#18211](https://github.com/netdata/netdata/pull/18211) ([ilyam8](https://github.com/ilyam8))
+- Port memcached collector to Go [\#18209](https://github.com/netdata/netdata/pull/18209) ([Ancairon](https://github.com/Ancairon))
+- Bump k8s.io/client-go from 0.30.2 to 0.30.3 in /src/go [\#18208](https://github.com/netdata/netdata/pull/18208) ([dependabot[bot]](https://github.com/apps/dependabot))
- docs: simplify "Disk Requirements and Retention" [\#18205](https://github.com/netdata/netdata/pull/18205) ([ilyam8](https://github.com/ilyam8))
- do not rely on the queued flag to queue a context [\#18198](https://github.com/netdata/netdata/pull/18198) ([ktsaou](https://github.com/ktsaou))
- Do not include REMOVED status in the alert snapshot [\#18197](https://github.com/netdata/netdata/pull/18197) ([stelfrag](https://github.com/stelfrag))
@@ -167,6 +175,10 @@
- add Win CPU interrupts [\#17753](https://github.com/netdata/netdata/pull/17753) ([thiagoftsm](https://github.com/thiagoftsm))
- Relax strict version constraints for DEB package dependencies. [\#17681](https://github.com/netdata/netdata/pull/17681) ([Ferroin](https://github.com/Ferroin))
+## [v1.46.3](https://github.com/netdata/netdata/tree/v1.46.3) (2024-07-23)
+
+[Full Changelog](https://github.com/netdata/netdata/compare/v1.46.2...v1.46.3)
+
## [v1.46.2](https://github.com/netdata/netdata/tree/v1.46.2) (2024-07-10)
[Full Changelog](https://github.com/netdata/netdata/compare/v1.46.1...v1.46.2)
@@ -407,16 +419,6 @@
- logs: add ND\_ALERT\_STATUS to facets [\#17641](https://github.com/netdata/netdata/pull/17641) ([ktsaou](https://github.com/ktsaou))
- Add valkey to apps\_groups.conf [\#17639](https://github.com/netdata/netdata/pull/17639) ([mohd-akram](https://github.com/mohd-akram))
- python.d remove hpssa [\#17638](https://github.com/netdata/netdata/pull/17638) ([ilyam8](https://github.com/ilyam8))
-- go.d hpssa [\#17637](https://github.com/netdata/netdata/pull/17637) ([ilyam8](https://github.com/ilyam8))
-- ndsudo add ssacli [\#17635](https://github.com/netdata/netdata/pull/17635) ([ilyam8](https://github.com/ilyam8))
-- health update isc dhcp alarms [\#17634](https://github.com/netdata/netdata/pull/17634) ([ilyam8](https://github.com/ilyam8))
-- add pcre2 to install-required-packages "netdata" for macOS [\#17633](https://github.com/netdata/netdata/pull/17633) ([ilyam8](https://github.com/ilyam8))
-- Bump github.com/docker/docker from 26.1.1+incompatible to 26.1.2+incompatible in /src/go/collectors/go.d.plugin [\#17631](https://github.com/netdata/netdata/pull/17631) ([dependabot[bot]](https://github.com/apps/dependabot))
-- Regenerate integrations.js [\#17630](https://github.com/netdata/netdata/pull/17630) ([netdatabot](https://github.com/netdatabot))
-- go.d isc\_dhcpd create a chart for each pool [\#17629](https://github.com/netdata/netdata/pull/17629) ([ilyam8](https://github.com/ilyam8))
-- python.d remove bind\_rndc [\#17628](https://github.com/netdata/netdata/pull/17628) ([ilyam8](https://github.com/ilyam8))
-- Add Sentry support to new CPack packages. [\#17627](https://github.com/netdata/netdata/pull/17627) ([Ferroin](https://github.com/Ferroin))
-- Regenerate integrations.js [\#17626](https://github.com/netdata/netdata/pull/17626) ([netdatabot](https://github.com/netdatabot))
## [v1.45.6](https://github.com/netdata/netdata/tree/v1.45.6) (2024-06-05)
diff --git a/CMakeLists.txt b/CMakeLists.txt
index 47510b4371d2f5..5b1c3bcb755634 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -2641,11 +2641,13 @@ install(PROGRAMS
COMPONENT netdata
DESTINATION usr/libexec/netdata/plugins.d)
-install(PROGRAMS
- src/health/notifications/alarm-email.sh
- src/health/notifications/alarm-test.sh
- COMPONENT netdata
- DESTINATION usr/libexec/netdata/plugins.d)
+if(CMAKE_BUILD_TYPE STREQUAL "Debug")
+ install(PROGRAMS
+ src/health/notifications/alarm-email.sh
+ src/health/notifications/alarm-test.sh
+ COMPONENT netdata
+ DESTINATION usr/libexec/netdata/plugins.d)
+endif()
install(FILES
src/health/notifications/health_alarm_notify.conf
@@ -2656,22 +2658,23 @@ install(FILES
# test/ files
#
-configure_file(tests/health_mgmtapi/health-cmdapi-test.sh.in tests/health_mgmtapi/health-cmdapi-test.sh @ONLY)
-configure_file(tests/acls/acl.sh.in tests/acls/acl.sh @ONLY)
-configure_file(tests/urls/request.sh.in tests/urls/request.sh @ONLY)
-configure_file(tests/alarm_repetition/alarm.sh.in tests/alarm_repetition/alarm.sh @ONLY)
-configure_file(tests/template_dimension/template_dim.sh.in tests/template_dimension/template_dim.sh @ONLY)
-configure_file(tests/ebpf/ebpf_thread_function.sh.in tests/ebpf/ebpf_thread_function.sh @ONLY)
-
-install(FILES
- ${CMAKE_BINARY_DIR}/tests/health_mgmtapi/health-cmdapi-test.sh
- ${CMAKE_BINARY_DIR}/tests/acls/acl.sh
- ${CMAKE_BINARY_DIR}/tests/urls/request.sh
- ${CMAKE_BINARY_DIR}/tests/alarm_repetition/alarm.sh
- ${CMAKE_BINARY_DIR}/tests/template_dimension/template_dim.sh
- ${CMAKE_BINARY_DIR}/tests/ebpf/ebpf_thread_function.sh
- DESTINATION usr/libexec/netdata/plugins.d)
+if(CMAKE_BUILD_TYPE STREQUAL "Debug")
+ configure_file(tests/health_mgmtapi/health-cmdapi-test.sh.in tests/health_mgmtapi/health-cmdapi-test.sh @ONLY)
+ configure_file(tests/acls/acl.sh.in tests/acls/acl.sh @ONLY)
+ configure_file(tests/urls/request.sh.in tests/urls/request.sh @ONLY)
+ configure_file(tests/alarm_repetition/alarm.sh.in tests/alarm_repetition/alarm.sh @ONLY)
+ configure_file(tests/template_dimension/template_dim.sh.in tests/template_dimension/template_dim.sh @ONLY)
+ configure_file(tests/ebpf/ebpf_thread_function.sh.in tests/ebpf/ebpf_thread_function.sh @ONLY)
+ install(FILES
+ ${CMAKE_BINARY_DIR}/tests/health_mgmtapi/health-cmdapi-test.sh
+ ${CMAKE_BINARY_DIR}/tests/acls/acl.sh
+ ${CMAKE_BINARY_DIR}/tests/urls/request.sh
+ ${CMAKE_BINARY_DIR}/tests/alarm_repetition/alarm.sh
+ ${CMAKE_BINARY_DIR}/tests/template_dimension/template_dim.sh
+ ${CMAKE_BINARY_DIR}/tests/ebpf/ebpf_thread_function.sh
+ DESTINATION usr/libexec/netdata/plugins.d)
+endif()
#
# charts.d plugin
#
@@ -2773,7 +2776,6 @@ install(FILES
src/collectors/python.d.plugin/gearman/gearman.conf
src/collectors/python.d.plugin/go_expvar/go_expvar.conf
src/collectors/python.d.plugin/haproxy/haproxy.conf
- src/collectors/python.d.plugin/memcached/memcached.conf
src/collectors/python.d.plugin/monit/monit.conf
src/collectors/python.d.plugin/nsd/nsd.conf
src/collectors/python.d.plugin/nvidia_smi/nvidia_smi.conf
@@ -2810,7 +2812,6 @@ install(FILES
src/collectors/python.d.plugin/gearman/gearman.chart.py
src/collectors/python.d.plugin/go_expvar/go_expvar.chart.py
src/collectors/python.d.plugin/haproxy/haproxy.chart.py
- src/collectors/python.d.plugin/memcached/memcached.chart.py
src/collectors/python.d.plugin/monit/monit.chart.py
src/collectors/python.d.plugin/nsd/nsd.chart.py
src/collectors/python.d.plugin/nvidia_smi/nvidia_smi.chart.py
diff --git a/integrations/integrations.js b/integrations/integrations.js
index b4a858f1dcca60..a6df6438565539 100644
--- a/integrations/integrations.js
+++ b/integrations/integrations.js
@@ -4946,12 +4946,51 @@ export const integrations = [
"setup": "## Setup\n\n### Prerequisites\n\nNo action required.\n\n### Configuration\n\n#### File\n\nThe configuration file name for this integration is `go.d/megacli.conf`.\n\n\nYou can edit the configuration file using the `edit-config` script from the\nNetdata [config directory](/docs/netdata-agent/configuration/README.md#the-netdata-config-directory).\n\n```bash\ncd /etc/netdata 2>/dev/null || cd /opt/netdata/etc/netdata\nsudo ./edit-config go.d/megacli.conf\n```\n#### Options\n\nThe following options can be defined globally: update_every.\n\n\n{% details open=true summary=\"Config options\" %}\n| Name | Description | Default | Required |\n|:----|:-----------|:-------|:--------:|\n| update_every | Data collection frequency. | 10 | no |\n| timeout | megacli binary execution timeout. | 2 | no |\n\n{% /details %}\n#### Examples\n\n##### Custom update_every\n\nAllows you to override the default data collection interval.\n\n{% details open=true summary=\"Config\" %}\n```yaml\njobs:\n - name: megacli\n update_every: 5 # Collect MegaCli Hardware RAID statistics every 5 seconds\n\n```\n{% /details %}\n",
"troubleshooting": "## Troubleshooting\n\n### Debug Mode\n\nTo troubleshoot issues with the `megacli` collector, run the `go.d.plugin` with the debug option enabled. The output\nshould give you clues as to why the collector isn't working.\n\n- Navigate to the `plugins.d` directory, usually at `/usr/libexec/netdata/plugins.d/`. If that's not the case on\n your system, open `netdata.conf` and look for the `plugins` setting under `[directories]`.\n\n ```bash\n cd /usr/libexec/netdata/plugins.d/\n ```\n\n- Switch to the `netdata` user.\n\n ```bash\n sudo -u netdata -s\n ```\n\n- Run the `go.d.plugin` to debug the collector:\n\n ```bash\n ./go.d.plugin -d -m megacli\n ```\n\n### Getting Logs\n\nIf you're encountering problems with the `megacli` collector, follow these steps to retrieve logs and identify potential issues:\n\n- **Run the command** specific to your system (systemd, non-systemd, or Docker container).\n- **Examine the output** for any warnings or error messages that might indicate issues. These messages should provide clues about the root cause of the problem.\n\n#### System with systemd\n\nUse the following command to view logs generated since the last Netdata service restart:\n\n```bash\njournalctl _SYSTEMD_INVOCATION_ID=\"$(systemctl show --value --property=InvocationID netdata)\" --namespace=netdata --grep megacli\n```\n\n#### System without systemd\n\nLocate the collector log file, typically at `/var/log/netdata/collector.log`, and use `grep` to filter for collector's name:\n\n```bash\ngrep megacli /var/log/netdata/collector.log\n```\n\n**Note**: This method shows logs from all restarts. Focus on the **latest entries** for troubleshooting current issues.\n\n#### Docker Container\n\nIf your Netdata runs in a Docker container named \"netdata\" (replace if different), use this command:\n\n```bash\ndocker logs netdata 2>&1 | grep megacli\n```\n\n",
"alerts": "## Alerts\n\n\nThe following alerts are available:\n\n| Alert name | On metric | Description |\n|:------------|:----------|:------------|\n| [ megacli_adapter_health_state ](https://github.com/netdata/netdata/blob/master/src/health/health.d/megacli.conf) | megacli.adapter_health_state | MegaCLI adapter ${label:adapter_number} is in the degraded state |\n| [ megacli_phys_drive_media_errors ](https://github.com/netdata/netdata/blob/master/src/health/health.d/megacli.conf) | megacli.phys_drive_media_errors | MegaCLI physical drive adapter ${label:adapter_number} slot ${label:slot_number} media errors |\n| [ megacli_phys_drive_predictive_failures ](https://github.com/netdata/netdata/blob/master/src/health/health.d/megacli.conf) | megacli.phys_drive_predictive_failures | MegaCLI physical drive (adapter ${label:adapter_number} slot ${label:slot_number}) predictive failures |\n| [ megacli_bbu_charge ](https://github.com/netdata/netdata/blob/master/src/health/health.d/megacli.conf) | megacli.bbu_charge | MegaCLI Backup Battery Unit (adapter ${label:adapter_number}) average charge over the last minute |\n| [ megacli_bbu_recharge_cycles ](https://github.com/netdata/netdata/blob/master/src/health/health.d/megacli.conf) | megacli.bbu_recharge_cycles | MegaCLI Backup Battery Unit (adapter ${label:adapter_number}) average charge over the last minute |\n",
- "metrics": "## Metrics\n\nMetrics grouped by *scope*.\n\nThe scope defines the instance that the metric belongs to. An instance is uniquely identified by a set of labels.\n\n\n\n### Per adapter\n\nThese metrics refer to the MegaCLI Adapter.\n\nLabels:\n\n| Label | Description |\n|:-----------|:----------------|\n| adapter_number | Adapter number |\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| megacli.adapter_health_state | optimal, degraded, partially_degraded, failed | state |\n\n### Per physical drive\n\nThese metrics refer to the MegaCLI Physical Drive.\n\nLabels:\n\n| Label | Description |\n|:-----------|:----------------|\n| adapter_number | Adapter number |\n| wwn | World Wide Name |\n| slot_number | Slot number |\n| drive_position | Position (e.g. DiskGroup: 0, Span: 0, Arm: 2) |\n| drive_type | Type (e.g. SATA) |\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| megacli.phys_drive_media_errors_rate | media_errors | errors/s |\n| megacli.phys_drive_predictive_failures_rate | predictive_failures | failures/s |\n\n### Per backup battery unit\n\nThese metrics refer to the MegaCLI Backup Battery Unit.\n\nLabels:\n\n| Label | Description |\n|:-----------|:----------------|\n| adapter_number | Adapter number |\n| battery_type | Battery type (e.g. BBU) |\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| megacli.bbu_relative_charge | charge | percentage |\n| megacli.bbu_recharge_cycles | recharge | cycles |\n| megacli.bbu_temperature | temperature | Celsius |\n\n",
+ "metrics": "## Metrics\n\nMetrics grouped by *scope*.\n\nThe scope defines the instance that the metric belongs to. An instance is uniquely identified by a set of labels.\n\n\n\n### Per adapter\n\nThese metrics refer to the MegaCLI Adapter.\n\nLabels:\n\n| Label | Description |\n|:-----------|:----------------|\n| adapter_number | Adapter number |\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| megacli.adapter_health_state | optimal, degraded, partially_degraded, failed | state |\n\n### Per physical drive\n\nThese metrics refer to the MegaCLI Physical Drive.\n\nLabels:\n\n| Label | Description |\n|:-----------|:----------------|\n| adapter_number | Adapter number |\n| wwn | World Wide Name |\n| slot_number | Slot number |\n| drive_position | Position (e.g. DiskGroup: 0, Span: 0, Arm: 2) |\n| drive_type | Type (e.g. SATA) |\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| megacli.phys_drive_media_errors_rate | media_errors | errors/s |\n| megacli.phys_drive_predictive_failures_rate | predictive_failures | failures/s |\n\n### Per backup battery unit\n\nThese metrics refer to the MegaCLI Backup Battery Unit.\n\nLabels:\n\n| Label | Description |\n|:-----------|:----------------|\n| adapter_number | Adapter number |\n| battery_type | Battery type (e.g. BBU) |\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| megacli.bbu_charge | charge | percentage |\n| megacli.bbu_recharge_cycles | recharge | cycles |\n| megacli.bbu_capacity_degradation | cap_degradation | percent |\n| megacli.bbu_temperature | temperature | Celsius |\n\n",
"integration_type": "collector",
"id": "go.d.plugin-megacli-MegaCLI_MegaRAID",
"edit_link": "https://github.com/netdata/netdata/blob/master/src/go/plugin/go.d/modules/megacli/metadata.yaml",
"related_resources": ""
},
+ {
+ "meta": {
+ "id": "collector-go.d.plugin-memcached",
+ "plugin_name": "go.d.plugin",
+ "module_name": "memcached",
+ "monitored_instance": {
+ "name": "Memcached",
+ "link": "https://memcached.org/",
+ "categories": [
+ "data-collection.database-servers"
+ ],
+ "icon_filename": "memcached.svg"
+ },
+ "related_resources": {
+ "integrations": {
+ "list": []
+ }
+ },
+ "info_provided_to_referring_integrations": {
+ "description": ""
+ },
+ "keywords": [
+ "memcached",
+ "memcache",
+ "cache",
+ "database"
+ ],
+ "most_popular": false
+ },
+ "overview": "# Memcached\n\nPlugin: go.d.plugin\nModule: memcached\n\n## Overview\n\nMonitor Memcached metrics for proficient in-memory key-value store operations. Track cache hits, misses, and memory usage for efficient data caching.\n\nIt reads the server's response to the `stats` command.\n\nThis collector is supported on all platforms.\n\nThis collector supports collecting metrics from multiple instances of this integration, including remote instances.\n\n\n### Default Behavior\n\n#### Auto-Detection\n\nIf no configuration is given, collector will attempt to connect to memcached instance on `127.0.0.1:11211` address.\n\n\n#### Limits\n\nThe default configuration for this integration does not impose any limits on data collection.\n\n#### Performance Impact\n\nThe default configuration for this integration is not expected to impose a significant performance impact on the system.\n",
+ "setup": "## Setup\n\n### Prerequisites\n\nNo action required.\n\n### Configuration\n\n#### File\n\nThe configuration file name for this integration is `go.d/memcached.conf`.\n\n\nYou can edit the configuration file using the `edit-config` script from the\nNetdata [config directory](/docs/netdata-agent/configuration/README.md#the-netdata-config-directory).\n\n```bash\ncd /etc/netdata 2>/dev/null || cd /opt/netdata/etc/netdata\nsudo ./edit-config go.d/memcached.conf\n```\n#### Options\n\nThe following options can be defined globally: update_every, autodetection_retry.\n\n\n{% details open=true summary=\"Config options\" %}\n| Name | Description | Default | Required |\n|:----|:-----------|:-------|:--------:|\n| update_every | Data collection frequency. | 1 | no |\n| autodetection_retry | Recheck interval in seconds. Zero means no recheck will be scheduled. | 0 | no |\n| address | The IP address and port where the memcached service listens for connections. | 127.0.0.1:11211 | yes |\n| timeout | Connection, read, and write timeout duration in seconds. The timeout includes name resolution. | 1 | no |\n\n{% /details %}\n#### Examples\n\n##### Basic\n\nA basic example configuration.\n\n{% details open=true summary=\"Config\" %}\n```yaml\njobs:\n - name: local\n address: 127.0.0.1:11211\n\n```\n{% /details %}\n##### Multi-instance\n\n> **Note**: When you define multiple jobs, their names must be unique.\n\nCollecting metrics from local and remote instances.\n\n\n{% details open=true summary=\"Config\" %}\n```yaml\njobs:\n - name: local\n address: 127.0.0.1:11211\n\n - name: remote\n address: 203.0.113.0:11211\n\n```\n{% /details %}\n",
+ "troubleshooting": "## Troubleshooting\n\n### Debug Mode\n\nTo troubleshoot issues with the `memcached` collector, run the `go.d.plugin` with the debug option enabled. The output\nshould give you clues as to why the collector isn't working.\n\n- Navigate to the `plugins.d` directory, usually at `/usr/libexec/netdata/plugins.d/`. If that's not the case on\n your system, open `netdata.conf` and look for the `plugins` setting under `[directories]`.\n\n ```bash\n cd /usr/libexec/netdata/plugins.d/\n ```\n\n- Switch to the `netdata` user.\n\n ```bash\n sudo -u netdata -s\n ```\n\n- Run the `go.d.plugin` to debug the collector:\n\n ```bash\n ./go.d.plugin -d -m memcached\n ```\n\n### Getting Logs\n\nIf you're encountering problems with the `memcached` collector, follow these steps to retrieve logs and identify potential issues:\n\n- **Run the command** specific to your system (systemd, non-systemd, or Docker container).\n- **Examine the output** for any warnings or error messages that might indicate issues. These messages should provide clues about the root cause of the problem.\n\n#### System with systemd\n\nUse the following command to view logs generated since the last Netdata service restart:\n\n```bash\njournalctl _SYSTEMD_INVOCATION_ID=\"$(systemctl show --value --property=InvocationID netdata)\" --namespace=netdata --grep memcached\n```\n\n#### System without systemd\n\nLocate the collector log file, typically at `/var/log/netdata/collector.log`, and use `grep` to filter for collector's name:\n\n```bash\ngrep memcached /var/log/netdata/collector.log\n```\n\n**Note**: This method shows logs from all restarts. Focus on the **latest entries** for troubleshooting current issues.\n\n#### Docker Container\n\nIf your Netdata runs in a Docker container named \"netdata\" (replace if different), use this command:\n\n```bash\ndocker logs netdata 2>&1 | grep memcached\n```\n\n",
+ "alerts": "## Alerts\n\n\nThe following alerts are available:\n\n| Alert name | On metric | Description |\n|:------------|:----------|:------------|\n| [ memcached_cache_memory_usage ](https://github.com/netdata/netdata/blob/master/src/health/health.d/memcached.conf) | memcached.cache | cache memory utilization |\n| [ memcached_cache_fill_rate ](https://github.com/netdata/netdata/blob/master/src/health/health.d/memcached.conf) | memcached.cache | average rate the cache fills up (positive), or frees up (negative) space over the last hour |\n| [ memcached_out_of_cache_space_time ](https://github.com/netdata/netdata/blob/master/src/health/health.d/memcached.conf) | memcached.cache | estimated time the cache will run out of space if the system continues to add data at the same rate as the past hour |\n",
+ "metrics": "## Metrics\n\nMetrics grouped by *scope*.\n\nThe scope defines the instance that the metric belongs to. An instance is uniquely identified by a set of labels.\n\n\n\n### Per Memcached instance\n\nThese metrics refer to the entire monitored application.\n\nThis scope has no labels.\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| memcached.cache | available, used | MiB |\n| memcached.net | in, out | kilobits/s |\n| memcached.connections | current, rejected, total | connections/s |\n| memcached.items | current, total | items |\n| memcached.evicted_reclaimed | reclaimed, evicted | items |\n| memcached.get | hints, misses | requests |\n| memcached.get_rate | rate | requests/s |\n| memcached.set_rate | rate | requests/s |\n| memcached.delete | hits, misses | requests |\n| memcached.cas | hits, misses, bad value | requests |\n| memcached.increment | hits, misses | requests |\n| memcached.decrement | hits, misses | requests |\n| memcached.touch | hits, misses | requests |\n| memcached.touch_rate | rate | requests/s |\n\n",
+ "integration_type": "collector",
+ "id": "go.d.plugin-memcached-Memcached",
+ "edit_link": "https://github.com/netdata/netdata/blob/master/src/go/plugin/go.d/modules/memcached/metadata.yaml",
+ "related_resources": ""
+ },
{
"meta": {
"id": "collector-go.d.plugin-mongodb",
@@ -18910,44 +18949,6 @@ export const integrations = [
"edit_link": "https://github.com/netdata/netdata/blob/master/src/collectors/python.d.plugin/go_expvar/metadata.yaml",
"related_resources": ""
},
- {
- "meta": {
- "plugin_name": "python.d.plugin",
- "module_name": "memcached",
- "monitored_instance": {
- "name": "Memcached",
- "link": "https://memcached.org/",
- "categories": [
- "data-collection.database-servers"
- ],
- "icon_filename": "memcached.svg"
- },
- "related_resources": {
- "integrations": {
- "list": []
- }
- },
- "info_provided_to_referring_integrations": {
- "description": ""
- },
- "keywords": [
- "memcached",
- "memcache",
- "cache",
- "database"
- ],
- "most_popular": false
- },
- "overview": "# Memcached\n\nPlugin: python.d.plugin\nModule: memcached\n\n## Overview\n\nMonitor Memcached metrics for proficient in-memory key-value store operations. Track cache hits, misses, and memory usage for efficient data caching.\n\nIt reads server response to stats command ([stats interface](https://github.com/memcached/memcached/wiki/Commands#stats)).\n\nThis collector is supported on all platforms.\n\nThis collector supports collecting metrics from multiple instances of this integration, including remote instances.\n\n\n### Default Behavior\n\n#### Auto-Detection\n\nIf no configuration is given, collector will attempt to connect to memcached instance on `127.0.0.1:11211` address.\n\n\n#### Limits\n\nThe default configuration for this integration does not impose any limits on data collection.\n\n#### Performance Impact\n\nThe default configuration for this integration is not expected to impose a significant performance impact on the system.\n",
- "setup": "## Setup\n\n### Prerequisites\n\nNo action required.\n\n### Configuration\n\n#### File\n\nThe configuration file name for this integration is `python.d/memcached.conf`.\n\n\nYou can edit the configuration file using the `edit-config` script from the\nNetdata [config directory](/docs/netdata-agent/configuration/README.md#the-netdata-config-directory).\n\n```bash\ncd /etc/netdata 2>/dev/null || cd /opt/netdata/etc/netdata\nsudo ./edit-config python.d/memcached.conf\n```\n#### Options\n\nThere are 2 sections:\n\n* Global variables\n* One or more JOBS that can define multiple different instances to monitor.\n\nThe following options can be defined globally: priority, penalty, autodetection_retry, update_every, but can also be defined per JOB to override the global values.\n\nAdditionally, the following collapsed table contains all the options that can be configured inside a JOB definition.\n\nEvery configuration JOB starts with a `job_name` value which will appear in the dashboard, unless a `name` parameter is specified.\n\n\n{% details open=true summary=\"Config options\" %}\n| Name | Description | Default | Required |\n|:----|:-----------|:-------|:--------:|\n| host | the host to connect to. | 127.0.0.1 | no |\n| port | the port to connect to. | 11211 | no |\n| update_every | Sets the default data collection frequency. | 10 | no |\n| priority | Controls the order of charts at the netdata dashboard. | 60000 | no |\n| autodetection_retry | Sets the job re-check interval in seconds. | 0 | no |\n| penalty | Indicates whether to apply penalty to update_every in case of failures. | yes | no |\n| name | Job name. This value will overwrite the `job_name` value. JOBS with the same name are mutually exclusive. Only one of them will be allowed running at any time. This allows autodetection to try several alternatives and pick the one that works. | | no |\n\n{% /details %}\n#### Examples\n\n##### localhost\n\nAn example configuration for localhost.\n\n```yaml\nlocalhost:\n name: 'local'\n host: 'localhost'\n port: 11211\n\n```\n##### localipv4\n\nAn example configuration for localipv4.\n\n{% details open=true summary=\"Config\" %}\n```yaml\nlocalhost:\n name: 'local'\n host: '127.0.0.1'\n port: 11211\n\n```\n{% /details %}\n##### localipv6\n\nAn example configuration for localipv6.\n\n{% details open=true summary=\"Config\" %}\n```yaml\nlocalhost:\n name: 'local'\n host: '::1'\n port: 11211\n\n```\n{% /details %}\n",
- "troubleshooting": "## Troubleshooting\n\n### Debug Mode\n\nTo troubleshoot issues with the `memcached` collector, run the `python.d.plugin` with the debug option enabled. The output\nshould give you clues as to why the collector isn't working.\n\n- Navigate to the `plugins.d` directory, usually at `/usr/libexec/netdata/plugins.d/`. If that's not the case on\n your system, open `netdata.conf` and look for the `plugins` setting under `[directories]`.\n\n ```bash\n cd /usr/libexec/netdata/plugins.d/\n ```\n\n- Switch to the `netdata` user.\n\n ```bash\n sudo -u netdata -s\n ```\n\n- Run the `python.d.plugin` to debug the collector:\n\n ```bash\n ./python.d.plugin memcached debug trace\n ```\n\n### Getting Logs\n\nIf you're encountering problems with the `memcached` collector, follow these steps to retrieve logs and identify potential issues:\n\n- **Run the command** specific to your system (systemd, non-systemd, or Docker container).\n- **Examine the output** for any warnings or error messages that might indicate issues. These messages should provide clues about the root cause of the problem.\n\n#### System with systemd\n\nUse the following command to view logs generated since the last Netdata service restart:\n\n```bash\njournalctl _SYSTEMD_INVOCATION_ID=\"$(systemctl show --value --property=InvocationID netdata)\" --namespace=netdata --grep memcached\n```\n\n#### System without systemd\n\nLocate the collector log file, typically at `/var/log/netdata/collector.log`, and use `grep` to filter for collector's name:\n\n```bash\ngrep memcached /var/log/netdata/collector.log\n```\n\n**Note**: This method shows logs from all restarts. Focus on the **latest entries** for troubleshooting current issues.\n\n#### Docker Container\n\nIf your Netdata runs in a Docker container named \"netdata\" (replace if different), use this command:\n\n```bash\ndocker logs netdata 2>&1 | grep memcached\n```\n\n",
- "alerts": "## Alerts\n\n\nThe following alerts are available:\n\n| Alert name | On metric | Description |\n|:------------|:----------|:------------|\n| [ memcached_cache_memory_usage ](https://github.com/netdata/netdata/blob/master/src/health/health.d/memcached.conf) | memcached.cache | cache memory utilization |\n| [ memcached_cache_fill_rate ](https://github.com/netdata/netdata/blob/master/src/health/health.d/memcached.conf) | memcached.cache | average rate the cache fills up (positive), or frees up (negative) space over the last hour |\n| [ memcached_out_of_cache_space_time ](https://github.com/netdata/netdata/blob/master/src/health/health.d/memcached.conf) | memcached.cache | estimated time the cache will run out of space if the system continues to add data at the same rate as the past hour |\n",
- "metrics": "## Metrics\n\nMetrics grouped by *scope*.\n\nThe scope defines the instance that the metric belongs to. An instance is uniquely identified by a set of labels.\n\n\n\n### Per Memcached instance\n\nThese metrics refer to the entire monitored application.\n\nThis scope has no labels.\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| memcached.cache | available, used | MiB |\n| memcached.net | in, out | kilobits/s |\n| memcached.connections | current, rejected, total | connections/s |\n| memcached.items | current, total | items |\n| memcached.evicted_reclaimed | reclaimed, evicted | items |\n| memcached.get | hints, misses | requests |\n| memcached.get_rate | rate | requests/s |\n| memcached.set_rate | rate | requests/s |\n| memcached.delete | hits, misses | requests |\n| memcached.cas | hits, misses, bad value | requests |\n| memcached.increment | hits, misses | requests |\n| memcached.decrement | hits, misses | requests |\n| memcached.touch | hits, misses | requests |\n| memcached.touch_rate | rate | requests/s |\n\n",
- "integration_type": "collector",
- "id": "python.d.plugin-memcached-Memcached",
- "edit_link": "https://github.com/netdata/netdata/blob/master/src/collectors/python.d.plugin/memcached/metadata.yaml",
- "related_resources": ""
- },
{
"meta": {
"plugin_name": "python.d.plugin",
diff --git a/integrations/integrations.json b/integrations/integrations.json
index 090ea082fd70b6..107b5aec726f2d 100644
--- a/integrations/integrations.json
+++ b/integrations/integrations.json
@@ -4944,12 +4944,51 @@
"setup": "## Setup\n\n### Prerequisites\n\nNo action required.\n\n### Configuration\n\n#### File\n\nThe configuration file name for this integration is `go.d/megacli.conf`.\n\n\nYou can edit the configuration file using the `edit-config` script from the\nNetdata [config directory](/docs/netdata-agent/configuration/README.md#the-netdata-config-directory).\n\n```bash\ncd /etc/netdata 2>/dev/null || cd /opt/netdata/etc/netdata\nsudo ./edit-config go.d/megacli.conf\n```\n#### Options\n\nThe following options can be defined globally: update_every.\n\n\n| Name | Description | Default | Required |\n|:----|:-----------|:-------|:--------:|\n| update_every | Data collection frequency. | 10 | no |\n| timeout | megacli binary execution timeout. | 2 | no |\n\n#### Examples\n\n##### Custom update_every\n\nAllows you to override the default data collection interval.\n\n```yaml\njobs:\n - name: megacli\n update_every: 5 # Collect MegaCli Hardware RAID statistics every 5 seconds\n\n```\n",
"troubleshooting": "## Troubleshooting\n\n### Debug Mode\n\nTo troubleshoot issues with the `megacli` collector, run the `go.d.plugin` with the debug option enabled. The output\nshould give you clues as to why the collector isn't working.\n\n- Navigate to the `plugins.d` directory, usually at `/usr/libexec/netdata/plugins.d/`. If that's not the case on\n your system, open `netdata.conf` and look for the `plugins` setting under `[directories]`.\n\n ```bash\n cd /usr/libexec/netdata/plugins.d/\n ```\n\n- Switch to the `netdata` user.\n\n ```bash\n sudo -u netdata -s\n ```\n\n- Run the `go.d.plugin` to debug the collector:\n\n ```bash\n ./go.d.plugin -d -m megacli\n ```\n\n### Getting Logs\n\nIf you're encountering problems with the `megacli` collector, follow these steps to retrieve logs and identify potential issues:\n\n- **Run the command** specific to your system (systemd, non-systemd, or Docker container).\n- **Examine the output** for any warnings or error messages that might indicate issues. These messages should provide clues about the root cause of the problem.\n\n#### System with systemd\n\nUse the following command to view logs generated since the last Netdata service restart:\n\n```bash\njournalctl _SYSTEMD_INVOCATION_ID=\"$(systemctl show --value --property=InvocationID netdata)\" --namespace=netdata --grep megacli\n```\n\n#### System without systemd\n\nLocate the collector log file, typically at `/var/log/netdata/collector.log`, and use `grep` to filter for collector's name:\n\n```bash\ngrep megacli /var/log/netdata/collector.log\n```\n\n**Note**: This method shows logs from all restarts. Focus on the **latest entries** for troubleshooting current issues.\n\n#### Docker Container\n\nIf your Netdata runs in a Docker container named \"netdata\" (replace if different), use this command:\n\n```bash\ndocker logs netdata 2>&1 | grep megacli\n```\n\n",
"alerts": "## Alerts\n\n\nThe following alerts are available:\n\n| Alert name | On metric | Description |\n|:------------|:----------|:------------|\n| [ megacli_adapter_health_state ](https://github.com/netdata/netdata/blob/master/src/health/health.d/megacli.conf) | megacli.adapter_health_state | MegaCLI adapter ${label:adapter_number} is in the degraded state |\n| [ megacli_phys_drive_media_errors ](https://github.com/netdata/netdata/blob/master/src/health/health.d/megacli.conf) | megacli.phys_drive_media_errors | MegaCLI physical drive adapter ${label:adapter_number} slot ${label:slot_number} media errors |\n| [ megacli_phys_drive_predictive_failures ](https://github.com/netdata/netdata/blob/master/src/health/health.d/megacli.conf) | megacli.phys_drive_predictive_failures | MegaCLI physical drive (adapter ${label:adapter_number} slot ${label:slot_number}) predictive failures |\n| [ megacli_bbu_charge ](https://github.com/netdata/netdata/blob/master/src/health/health.d/megacli.conf) | megacli.bbu_charge | MegaCLI Backup Battery Unit (adapter ${label:adapter_number}) average charge over the last minute |\n| [ megacli_bbu_recharge_cycles ](https://github.com/netdata/netdata/blob/master/src/health/health.d/megacli.conf) | megacli.bbu_recharge_cycles | MegaCLI Backup Battery Unit (adapter ${label:adapter_number}) average charge over the last minute |\n",
- "metrics": "## Metrics\n\nMetrics grouped by *scope*.\n\nThe scope defines the instance that the metric belongs to. An instance is uniquely identified by a set of labels.\n\n\n\n### Per adapter\n\nThese metrics refer to the MegaCLI Adapter.\n\nLabels:\n\n| Label | Description |\n|:-----------|:----------------|\n| adapter_number | Adapter number |\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| megacli.adapter_health_state | optimal, degraded, partially_degraded, failed | state |\n\n### Per physical drive\n\nThese metrics refer to the MegaCLI Physical Drive.\n\nLabels:\n\n| Label | Description |\n|:-----------|:----------------|\n| adapter_number | Adapter number |\n| wwn | World Wide Name |\n| slot_number | Slot number |\n| drive_position | Position (e.g. DiskGroup: 0, Span: 0, Arm: 2) |\n| drive_type | Type (e.g. SATA) |\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| megacli.phys_drive_media_errors_rate | media_errors | errors/s |\n| megacli.phys_drive_predictive_failures_rate | predictive_failures | failures/s |\n\n### Per backup battery unit\n\nThese metrics refer to the MegaCLI Backup Battery Unit.\n\nLabels:\n\n| Label | Description |\n|:-----------|:----------------|\n| adapter_number | Adapter number |\n| battery_type | Battery type (e.g. BBU) |\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| megacli.bbu_relative_charge | charge | percentage |\n| megacli.bbu_recharge_cycles | recharge | cycles |\n| megacli.bbu_temperature | temperature | Celsius |\n\n",
+ "metrics": "## Metrics\n\nMetrics grouped by *scope*.\n\nThe scope defines the instance that the metric belongs to. An instance is uniquely identified by a set of labels.\n\n\n\n### Per adapter\n\nThese metrics refer to the MegaCLI Adapter.\n\nLabels:\n\n| Label | Description |\n|:-----------|:----------------|\n| adapter_number | Adapter number |\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| megacli.adapter_health_state | optimal, degraded, partially_degraded, failed | state |\n\n### Per physical drive\n\nThese metrics refer to the MegaCLI Physical Drive.\n\nLabels:\n\n| Label | Description |\n|:-----------|:----------------|\n| adapter_number | Adapter number |\n| wwn | World Wide Name |\n| slot_number | Slot number |\n| drive_position | Position (e.g. DiskGroup: 0, Span: 0, Arm: 2) |\n| drive_type | Type (e.g. SATA) |\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| megacli.phys_drive_media_errors_rate | media_errors | errors/s |\n| megacli.phys_drive_predictive_failures_rate | predictive_failures | failures/s |\n\n### Per backup battery unit\n\nThese metrics refer to the MegaCLI Backup Battery Unit.\n\nLabels:\n\n| Label | Description |\n|:-----------|:----------------|\n| adapter_number | Adapter number |\n| battery_type | Battery type (e.g. BBU) |\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| megacli.bbu_charge | charge | percentage |\n| megacli.bbu_recharge_cycles | recharge | cycles |\n| megacli.bbu_capacity_degradation | cap_degradation | percent |\n| megacli.bbu_temperature | temperature | Celsius |\n\n",
"integration_type": "collector",
"id": "go.d.plugin-megacli-MegaCLI_MegaRAID",
"edit_link": "https://github.com/netdata/netdata/blob/master/src/go/plugin/go.d/modules/megacli/metadata.yaml",
"related_resources": ""
},
+ {
+ "meta": {
+ "id": "collector-go.d.plugin-memcached",
+ "plugin_name": "go.d.plugin",
+ "module_name": "memcached",
+ "monitored_instance": {
+ "name": "Memcached",
+ "link": "https://memcached.org/",
+ "categories": [
+ "data-collection.database-servers"
+ ],
+ "icon_filename": "memcached.svg"
+ },
+ "related_resources": {
+ "integrations": {
+ "list": []
+ }
+ },
+ "info_provided_to_referring_integrations": {
+ "description": ""
+ },
+ "keywords": [
+ "memcached",
+ "memcache",
+ "cache",
+ "database"
+ ],
+ "most_popular": false
+ },
+ "overview": "# Memcached\n\nPlugin: go.d.plugin\nModule: memcached\n\n## Overview\n\nMonitor Memcached metrics for proficient in-memory key-value store operations. Track cache hits, misses, and memory usage for efficient data caching.\n\nIt reads the server's response to the `stats` command.\n\nThis collector is supported on all platforms.\n\nThis collector supports collecting metrics from multiple instances of this integration, including remote instances.\n\n\n### Default Behavior\n\n#### Auto-Detection\n\nIf no configuration is given, collector will attempt to connect to memcached instance on `127.0.0.1:11211` address.\n\n\n#### Limits\n\nThe default configuration for this integration does not impose any limits on data collection.\n\n#### Performance Impact\n\nThe default configuration for this integration is not expected to impose a significant performance impact on the system.\n",
+ "setup": "## Setup\n\n### Prerequisites\n\nNo action required.\n\n### Configuration\n\n#### File\n\nThe configuration file name for this integration is `go.d/memcached.conf`.\n\n\nYou can edit the configuration file using the `edit-config` script from the\nNetdata [config directory](/docs/netdata-agent/configuration/README.md#the-netdata-config-directory).\n\n```bash\ncd /etc/netdata 2>/dev/null || cd /opt/netdata/etc/netdata\nsudo ./edit-config go.d/memcached.conf\n```\n#### Options\n\nThe following options can be defined globally: update_every, autodetection_retry.\n\n\n| Name | Description | Default | Required |\n|:----|:-----------|:-------|:--------:|\n| update_every | Data collection frequency. | 1 | no |\n| autodetection_retry | Recheck interval in seconds. Zero means no recheck will be scheduled. | 0 | no |\n| address | The IP address and port where the memcached service listens for connections. | 127.0.0.1:11211 | yes |\n| timeout | Connection, read, and write timeout duration in seconds. The timeout includes name resolution. | 1 | no |\n\n#### Examples\n\n##### Basic\n\nA basic example configuration.\n\n```yaml\njobs:\n - name: local\n address: 127.0.0.1:11211\n\n```\n##### Multi-instance\n\n> **Note**: When you define multiple jobs, their names must be unique.\n\nCollecting metrics from local and remote instances.\n\n\n```yaml\njobs:\n - name: local\n address: 127.0.0.1:11211\n\n - name: remote\n address: 203.0.113.0:11211\n\n```\n",
+ "troubleshooting": "## Troubleshooting\n\n### Debug Mode\n\nTo troubleshoot issues with the `memcached` collector, run the `go.d.plugin` with the debug option enabled. The output\nshould give you clues as to why the collector isn't working.\n\n- Navigate to the `plugins.d` directory, usually at `/usr/libexec/netdata/plugins.d/`. If that's not the case on\n your system, open `netdata.conf` and look for the `plugins` setting under `[directories]`.\n\n ```bash\n cd /usr/libexec/netdata/plugins.d/\n ```\n\n- Switch to the `netdata` user.\n\n ```bash\n sudo -u netdata -s\n ```\n\n- Run the `go.d.plugin` to debug the collector:\n\n ```bash\n ./go.d.plugin -d -m memcached\n ```\n\n### Getting Logs\n\nIf you're encountering problems with the `memcached` collector, follow these steps to retrieve logs and identify potential issues:\n\n- **Run the command** specific to your system (systemd, non-systemd, or Docker container).\n- **Examine the output** for any warnings or error messages that might indicate issues. These messages should provide clues about the root cause of the problem.\n\n#### System with systemd\n\nUse the following command to view logs generated since the last Netdata service restart:\n\n```bash\njournalctl _SYSTEMD_INVOCATION_ID=\"$(systemctl show --value --property=InvocationID netdata)\" --namespace=netdata --grep memcached\n```\n\n#### System without systemd\n\nLocate the collector log file, typically at `/var/log/netdata/collector.log`, and use `grep` to filter for collector's name:\n\n```bash\ngrep memcached /var/log/netdata/collector.log\n```\n\n**Note**: This method shows logs from all restarts. Focus on the **latest entries** for troubleshooting current issues.\n\n#### Docker Container\n\nIf your Netdata runs in a Docker container named \"netdata\" (replace if different), use this command:\n\n```bash\ndocker logs netdata 2>&1 | grep memcached\n```\n\n",
+ "alerts": "## Alerts\n\n\nThe following alerts are available:\n\n| Alert name | On metric | Description |\n|:------------|:----------|:------------|\n| [ memcached_cache_memory_usage ](https://github.com/netdata/netdata/blob/master/src/health/health.d/memcached.conf) | memcached.cache | cache memory utilization |\n| [ memcached_cache_fill_rate ](https://github.com/netdata/netdata/blob/master/src/health/health.d/memcached.conf) | memcached.cache | average rate the cache fills up (positive), or frees up (negative) space over the last hour |\n| [ memcached_out_of_cache_space_time ](https://github.com/netdata/netdata/blob/master/src/health/health.d/memcached.conf) | memcached.cache | estimated time the cache will run out of space if the system continues to add data at the same rate as the past hour |\n",
+ "metrics": "## Metrics\n\nMetrics grouped by *scope*.\n\nThe scope defines the instance that the metric belongs to. An instance is uniquely identified by a set of labels.\n\n\n\n### Per Memcached instance\n\nThese metrics refer to the entire monitored application.\n\nThis scope has no labels.\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| memcached.cache | available, used | MiB |\n| memcached.net | in, out | kilobits/s |\n| memcached.connections | current, rejected, total | connections/s |\n| memcached.items | current, total | items |\n| memcached.evicted_reclaimed | reclaimed, evicted | items |\n| memcached.get | hints, misses | requests |\n| memcached.get_rate | rate | requests/s |\n| memcached.set_rate | rate | requests/s |\n| memcached.delete | hits, misses | requests |\n| memcached.cas | hits, misses, bad value | requests |\n| memcached.increment | hits, misses | requests |\n| memcached.decrement | hits, misses | requests |\n| memcached.touch | hits, misses | requests |\n| memcached.touch_rate | rate | requests/s |\n\n",
+ "integration_type": "collector",
+ "id": "go.d.plugin-memcached-Memcached",
+ "edit_link": "https://github.com/netdata/netdata/blob/master/src/go/plugin/go.d/modules/memcached/metadata.yaml",
+ "related_resources": ""
+ },
{
"meta": {
"id": "collector-go.d.plugin-mongodb",
@@ -18908,44 +18947,6 @@
"edit_link": "https://github.com/netdata/netdata/blob/master/src/collectors/python.d.plugin/go_expvar/metadata.yaml",
"related_resources": ""
},
- {
- "meta": {
- "plugin_name": "python.d.plugin",
- "module_name": "memcached",
- "monitored_instance": {
- "name": "Memcached",
- "link": "https://memcached.org/",
- "categories": [
- "data-collection.database-servers"
- ],
- "icon_filename": "memcached.svg"
- },
- "related_resources": {
- "integrations": {
- "list": []
- }
- },
- "info_provided_to_referring_integrations": {
- "description": ""
- },
- "keywords": [
- "memcached",
- "memcache",
- "cache",
- "database"
- ],
- "most_popular": false
- },
- "overview": "# Memcached\n\nPlugin: python.d.plugin\nModule: memcached\n\n## Overview\n\nMonitor Memcached metrics for proficient in-memory key-value store operations. Track cache hits, misses, and memory usage for efficient data caching.\n\nIt reads server response to stats command ([stats interface](https://github.com/memcached/memcached/wiki/Commands#stats)).\n\nThis collector is supported on all platforms.\n\nThis collector supports collecting metrics from multiple instances of this integration, including remote instances.\n\n\n### Default Behavior\n\n#### Auto-Detection\n\nIf no configuration is given, collector will attempt to connect to memcached instance on `127.0.0.1:11211` address.\n\n\n#### Limits\n\nThe default configuration for this integration does not impose any limits on data collection.\n\n#### Performance Impact\n\nThe default configuration for this integration is not expected to impose a significant performance impact on the system.\n",
- "setup": "## Setup\n\n### Prerequisites\n\nNo action required.\n\n### Configuration\n\n#### File\n\nThe configuration file name for this integration is `python.d/memcached.conf`.\n\n\nYou can edit the configuration file using the `edit-config` script from the\nNetdata [config directory](/docs/netdata-agent/configuration/README.md#the-netdata-config-directory).\n\n```bash\ncd /etc/netdata 2>/dev/null || cd /opt/netdata/etc/netdata\nsudo ./edit-config python.d/memcached.conf\n```\n#### Options\n\nThere are 2 sections:\n\n* Global variables\n* One or more JOBS that can define multiple different instances to monitor.\n\nThe following options can be defined globally: priority, penalty, autodetection_retry, update_every, but can also be defined per JOB to override the global values.\n\nAdditionally, the following collapsed table contains all the options that can be configured inside a JOB definition.\n\nEvery configuration JOB starts with a `job_name` value which will appear in the dashboard, unless a `name` parameter is specified.\n\n\n| Name | Description | Default | Required |\n|:----|:-----------|:-------|:--------:|\n| host | the host to connect to. | 127.0.0.1 | no |\n| port | the port to connect to. | 11211 | no |\n| update_every | Sets the default data collection frequency. | 10 | no |\n| priority | Controls the order of charts at the netdata dashboard. | 60000 | no |\n| autodetection_retry | Sets the job re-check interval in seconds. | 0 | no |\n| penalty | Indicates whether to apply penalty to update_every in case of failures. | yes | no |\n| name | Job name. This value will overwrite the `job_name` value. JOBS with the same name are mutually exclusive. Only one of them will be allowed running at any time. This allows autodetection to try several alternatives and pick the one that works. | | no |\n\n#### Examples\n\n##### localhost\n\nAn example configuration for localhost.\n\n```yaml\nlocalhost:\n name: 'local'\n host: 'localhost'\n port: 11211\n\n```\n##### localipv4\n\nAn example configuration for localipv4.\n\n```yaml\nlocalhost:\n name: 'local'\n host: '127.0.0.1'\n port: 11211\n\n```\n##### localipv6\n\nAn example configuration for localipv6.\n\n```yaml\nlocalhost:\n name: 'local'\n host: '::1'\n port: 11211\n\n```\n",
- "troubleshooting": "## Troubleshooting\n\n### Debug Mode\n\nTo troubleshoot issues with the `memcached` collector, run the `python.d.plugin` with the debug option enabled. The output\nshould give you clues as to why the collector isn't working.\n\n- Navigate to the `plugins.d` directory, usually at `/usr/libexec/netdata/plugins.d/`. If that's not the case on\n your system, open `netdata.conf` and look for the `plugins` setting under `[directories]`.\n\n ```bash\n cd /usr/libexec/netdata/plugins.d/\n ```\n\n- Switch to the `netdata` user.\n\n ```bash\n sudo -u netdata -s\n ```\n\n- Run the `python.d.plugin` to debug the collector:\n\n ```bash\n ./python.d.plugin memcached debug trace\n ```\n\n### Getting Logs\n\nIf you're encountering problems with the `memcached` collector, follow these steps to retrieve logs and identify potential issues:\n\n- **Run the command** specific to your system (systemd, non-systemd, or Docker container).\n- **Examine the output** for any warnings or error messages that might indicate issues. These messages should provide clues about the root cause of the problem.\n\n#### System with systemd\n\nUse the following command to view logs generated since the last Netdata service restart:\n\n```bash\njournalctl _SYSTEMD_INVOCATION_ID=\"$(systemctl show --value --property=InvocationID netdata)\" --namespace=netdata --grep memcached\n```\n\n#### System without systemd\n\nLocate the collector log file, typically at `/var/log/netdata/collector.log`, and use `grep` to filter for collector's name:\n\n```bash\ngrep memcached /var/log/netdata/collector.log\n```\n\n**Note**: This method shows logs from all restarts. Focus on the **latest entries** for troubleshooting current issues.\n\n#### Docker Container\n\nIf your Netdata runs in a Docker container named \"netdata\" (replace if different), use this command:\n\n```bash\ndocker logs netdata 2>&1 | grep memcached\n```\n\n",
- "alerts": "## Alerts\n\n\nThe following alerts are available:\n\n| Alert name | On metric | Description |\n|:------------|:----------|:------------|\n| [ memcached_cache_memory_usage ](https://github.com/netdata/netdata/blob/master/src/health/health.d/memcached.conf) | memcached.cache | cache memory utilization |\n| [ memcached_cache_fill_rate ](https://github.com/netdata/netdata/blob/master/src/health/health.d/memcached.conf) | memcached.cache | average rate the cache fills up (positive), or frees up (negative) space over the last hour |\n| [ memcached_out_of_cache_space_time ](https://github.com/netdata/netdata/blob/master/src/health/health.d/memcached.conf) | memcached.cache | estimated time the cache will run out of space if the system continues to add data at the same rate as the past hour |\n",
- "metrics": "## Metrics\n\nMetrics grouped by *scope*.\n\nThe scope defines the instance that the metric belongs to. An instance is uniquely identified by a set of labels.\n\n\n\n### Per Memcached instance\n\nThese metrics refer to the entire monitored application.\n\nThis scope has no labels.\n\nMetrics:\n\n| Metric | Dimensions | Unit |\n|:------|:----------|:----|\n| memcached.cache | available, used | MiB |\n| memcached.net | in, out | kilobits/s |\n| memcached.connections | current, rejected, total | connections/s |\n| memcached.items | current, total | items |\n| memcached.evicted_reclaimed | reclaimed, evicted | items |\n| memcached.get | hints, misses | requests |\n| memcached.get_rate | rate | requests/s |\n| memcached.set_rate | rate | requests/s |\n| memcached.delete | hits, misses | requests |\n| memcached.cas | hits, misses, bad value | requests |\n| memcached.increment | hits, misses | requests |\n| memcached.decrement | hits, misses | requests |\n| memcached.touch | hits, misses | requests |\n| memcached.touch_rate | rate | requests/s |\n\n",
- "integration_type": "collector",
- "id": "python.d.plugin-memcached-Memcached",
- "edit_link": "https://github.com/netdata/netdata/blob/master/src/collectors/python.d.plugin/memcached/metadata.yaml",
- "related_resources": ""
- },
{
"meta": {
"plugin_name": "python.d.plugin",
diff --git a/netdata.spec.in b/netdata.spec.in
index 74fe03b1861086..67d7de4a08e3dc 100644
--- a/netdata.spec.in
+++ b/netdata.spec.in
@@ -527,22 +527,14 @@ rm -rf "${RPM_BUILD_ROOT}"
%{_libexecdir}/%{name}/install-service.sh
%{_libexecdir}/%{name}/%{name}-updater.sh
%{_libexecdir}/%{name}/%{name}-uninstaller.sh
-%{_libexecdir}/%{name}/plugins.d/acl.sh
-%{_libexecdir}/%{name}/plugins.d/alarm.sh
-%{_libexecdir}/%{name}/plugins.d/alarm-email.sh
%{_libexecdir}/%{name}/plugins.d/alarm-notify.sh
-%{_libexecdir}/%{name}/plugins.d/alarm-test.sh
%{_libexecdir}/%{name}/plugins.d/anonymous-statistics.sh
%{_libexecdir}/%{name}/plugins.d/cgroup-name.sh
%{_libexecdir}/%{name}/plugins.d/get-kubernetes-labels.sh
-%{_libexecdir}/%{name}/plugins.d/health-cmdapi-test.sh
%{_libexecdir}/%{name}/plugins.d/ioping.plugin
%{_libexecdir}/%{name}/plugins.d/loopsleepms.sh.inc
-%{_libexecdir}/%{name}/plugins.d/request.sh
%{_libexecdir}/%{name}/plugins.d/system-info.sh
%{_libexecdir}/%{name}/plugins.d/tc-qos-helper.sh
-%{_libexecdir}/%{name}/plugins.d/template_dim.sh
-%{_libexecdir}/%{name}/plugins.d/ebpf_thread_function.sh
# cgroup-network detects the network interfaces of CGROUPs
# it must be able to use setns() and run cgroup-network-helper.sh as root
diff --git a/packaging/version b/packaging/version
index 73c325e2f3b73a..2b137de36faaf7 100644
--- a/packaging/version
+++ b/packaging/version
@@ -1 +1 @@
-v1.46.0-194-nightly
+v1.46.0-204-nightly
diff --git a/src/collectors/COLLECTORS.md b/src/collectors/COLLECTORS.md
index 2978e233d2509c..5365490d7d6e01 100644
--- a/src/collectors/COLLECTORS.md
+++ b/src/collectors/COLLECTORS.md
@@ -239,7 +239,7 @@ If you don't see the app/service you'd like to monitor in this list:
- [Memcached (community)](https://github.com/netdata/netdata/blob/master/src/go/plugin/go.d/modules/prometheus/integrations/memcached_community.md)
-- [Memcached](https://github.com/netdata/netdata/blob/master/src/collectors/python.d.plugin/memcached/integrations/memcached.md)
+- [Memcached](https://github.com/netdata/netdata/blob/master/src/go/plugin/go.d/modules/memcached/integrations/memcached.md)
- [MongoDB](https://github.com/netdata/netdata/blob/master/src/go/plugin/go.d/modules/mongodb/integrations/mongodb.md)
diff --git a/src/collectors/python.d.plugin/memcached/memcached.chart.py b/src/collectors/python.d.plugin/memcached/memcached.chart.py
deleted file mode 100644
index adb9560b74cf5d..00000000000000
--- a/src/collectors/python.d.plugin/memcached/memcached.chart.py
+++ /dev/null
@@ -1,197 +0,0 @@
-# -*- coding: utf-8 -*-
-# Description: memcached netdata python.d module
-# Author: Pawel Krupa (paulfantom)
-# SPDX-License-Identifier: GPL-3.0-or-later
-
-from bases.FrameworkServices.SocketService import SocketService
-
-ORDER = [
- 'cache',
- 'net',
- 'connections',
- 'items',
- 'evicted_reclaimed',
- 'get',
- 'get_rate',
- 'set_rate',
- 'cas',
- 'delete',
- 'increment',
- 'decrement',
- 'touch',
- 'touch_rate',
-]
-
-CHARTS = {
- 'cache': {
- 'options': [None, 'Cache Size', 'MiB', 'cache', 'memcached.cache', 'stacked'],
- 'lines': [
- ['avail', 'available', 'absolute', 1, 1 << 20],
- ['used', 'used', 'absolute', 1, 1 << 20]
- ]
- },
- 'net': {
- 'options': [None, 'Network', 'kilobits/s', 'network', 'memcached.net', 'area'],
- 'lines': [
- ['bytes_read', 'in', 'incremental', 8, 1000],
- ['bytes_written', 'out', 'incremental', -8, 1000],
- ]
- },
- 'connections': {
- 'options': [None, 'Connections', 'connections/s', 'connections', 'memcached.connections', 'line'],
- 'lines': [
- ['curr_connections', 'current', 'incremental'],
- ['rejected_connections', 'rejected', 'incremental'],
- ['total_connections', 'total', 'incremental']
- ]
- },
- 'items': {
- 'options': [None, 'Items', 'items', 'items', 'memcached.items', 'line'],
- 'lines': [
- ['curr_items', 'current', 'absolute'],
- ['total_items', 'total', 'absolute']
- ]
- },
- 'evicted_reclaimed': {
- 'options': [None, 'Evicted and Reclaimed Items', 'items', 'items', 'memcached.evicted_reclaimed', 'line'],
- 'lines': [
- ['reclaimed', 'reclaimed', 'absolute'],
- ['evictions', 'evicted', 'absolute']
- ]
- },
- 'get': {
- 'options': [None, 'Get Requests', 'requests', 'get ops', 'memcached.get', 'stacked'],
- 'lines': [
- ['get_hits', 'hits', 'percent-of-absolute-row'],
- ['get_misses', 'misses', 'percent-of-absolute-row']
- ]
- },
- 'get_rate': {
- 'options': [None, 'Get Request Rate', 'requests/s', 'get ops', 'memcached.get_rate', 'line'],
- 'lines': [
- ['cmd_get', 'rate', 'incremental']
- ]
- },
- 'set_rate': {
- 'options': [None, 'Set Request Rate', 'requests/s', 'set ops', 'memcached.set_rate', 'line'],
- 'lines': [
- ['cmd_set', 'rate', 'incremental']
- ]
- },
- 'delete': {
- 'options': [None, 'Delete Requests', 'requests', 'delete ops', 'memcached.delete', 'stacked'],
- 'lines': [
- ['delete_hits', 'hits', 'percent-of-absolute-row'],
- ['delete_misses', 'misses', 'percent-of-absolute-row'],
- ]
- },
- 'cas': {
- 'options': [None, 'Check and Set Requests', 'requests', 'check and set ops', 'memcached.cas', 'stacked'],
- 'lines': [
- ['cas_hits', 'hits', 'percent-of-absolute-row'],
- ['cas_misses', 'misses', 'percent-of-absolute-row'],
- ['cas_badval', 'bad value', 'percent-of-absolute-row']
- ]
- },
- 'increment': {
- 'options': [None, 'Increment Requests', 'requests', 'increment ops', 'memcached.increment', 'stacked'],
- 'lines': [
- ['incr_hits', 'hits', 'percent-of-absolute-row'],
- ['incr_misses', 'misses', 'percent-of-absolute-row']
- ]
- },
- 'decrement': {
- 'options': [None, 'Decrement Requests', 'requests', 'decrement ops', 'memcached.decrement', 'stacked'],
- 'lines': [
- ['decr_hits', 'hits', 'percent-of-absolute-row'],
- ['decr_misses', 'misses', 'percent-of-absolute-row']
- ]
- },
- 'touch': {
- 'options': [None, 'Touch Requests', 'requests', 'touch ops', 'memcached.touch', 'stacked'],
- 'lines': [
- ['touch_hits', 'hits', 'percent-of-absolute-row'],
- ['touch_misses', 'misses', 'percent-of-absolute-row']
- ]
- },
- 'touch_rate': {
- 'options': [None, 'Touch Request Rate', 'requests/s', 'touch ops', 'memcached.touch_rate', 'line'],
- 'lines': [
- ['cmd_touch', 'rate', 'incremental']
- ]
- }
-}
-
-
-class Service(SocketService):
- def __init__(self, configuration=None, name=None):
- SocketService.__init__(self, configuration=configuration, name=name)
- self.order = ORDER
- self.definitions = CHARTS
- self.request = 'stats\r\n'
- self.host = 'localhost'
- self.port = 11211
- self._keep_alive = True
- self.unix_socket = None
-
- def _get_data(self):
- """
- Get data from socket
- :return: dict
- """
- response = self._get_raw_data()
- if response is None:
- # error has already been logged
- return None
-
- if response.startswith('ERROR'):
- self.error('received ERROR')
- return None
-
- try:
- parsed = response.split('\n')
- except AttributeError:
- self.error('response is invalid/empty')
- return None
-
- # split the response
- data = {}
- for line in parsed:
- if line.startswith('STAT'):
- try:
- t = line[5:].split(' ')
- data[t[0]] = t[1]
- except (IndexError, ValueError):
- self.debug('invalid line received: ' + str(line))
-
- if not data:
- self.error("received data doesn't have any records")
- return None
-
- # custom calculations
- try:
- data['avail'] = int(data['limit_maxbytes']) - int(data['bytes'])
- data['used'] = int(data['bytes'])
- except (KeyError, ValueError, TypeError):
- pass
-
- return data
-
- def _check_raw_data(self, data):
- if data.endswith('END\r\n'):
- self.debug('received full response from memcached')
- return True
-
- self.debug('waiting more data from memcached')
- return False
-
- def check(self):
- """
- Parse configuration, check if memcached is available
- :return: boolean
- """
- self._parse_config()
- data = self._get_data()
- if data is None:
- return False
- return True
diff --git a/src/collectors/python.d.plugin/memcached/memcached.conf b/src/collectors/python.d.plugin/memcached/memcached.conf
deleted file mode 100644
index 3286b46230a5fa..00000000000000
--- a/src/collectors/python.d.plugin/memcached/memcached.conf
+++ /dev/null
@@ -1,90 +0,0 @@
-# netdata python.d.plugin configuration for memcached
-#
-# This file is in YaML format. Generally the format is:
-#
-# name: value
-#
-# There are 2 sections:
-# - global variables
-# - one or more JOBS
-#
-# JOBS allow you to collect values from multiple sources.
-# Each source will have its own set of charts.
-#
-# JOB parameters have to be indented (using spaces only, example below).
-
-# ----------------------------------------------------------------------
-# Global Variables
-# These variables set the defaults for all JOBs, however each JOB
-# may define its own, overriding the defaults.
-
-# update_every sets the default data collection frequency.
-# If unset, the python.d.plugin default is used.
-# update_every: 1
-
-# priority controls the order of charts at the netdata dashboard.
-# Lower numbers move the charts towards the top of the page.
-# If unset, the default for python.d.plugin is used.
-# priority: 60000
-
-# penalty indicates whether to apply penalty to update_every in case of failures.
-# Penalty will increase every 5 failed updates in a row. Maximum penalty is 10 minutes.
-# penalty: yes
-
-# autodetection_retry sets the job re-check interval in seconds.
-# The job is not deleted if check fails.
-# Attempts to start the job are made once every autodetection_retry.
-# This feature is disabled by default.
-# autodetection_retry: 0
-
-# ----------------------------------------------------------------------
-# JOBS (data collection sources)
-#
-# The default JOBS share the same *name*. JOBS with the same name
-# are mutually exclusive. Only one of them will be allowed running at
-# any time. This allows autodetection to try several alternatives and
-# pick the one that works.
-#
-# Any number of jobs is supported.
-#
-# All python.d.plugin JOBS (for all its modules) support a set of
-# predefined parameters. These are:
-#
-# job_name:
-# name: myname # the JOB's name as it will appear at the
-# # dashboard (by default is the job_name)
-# # JOBs sharing a name are mutually exclusive
-# update_every: 1 # the JOB's data collection frequency
-# priority: 60000 # the JOB's order on the dashboard
-# penalty: yes # the JOB's penalty
-# autodetection_retry: 0 # the JOB's re-check interval in seconds
-#
-# Additionally to the above, memcached also supports the following:
-#
-# socket: 'path/to/memcached.sock'
-#
-# or
-# host: 'IP or HOSTNAME' # the host to connect to
-# port: PORT # the port to connect to
-#
-#
-
-# ----------------------------------------------------------------------
-# AUTO-DETECTION JOBS
-# only one of them will run (they have the same name)
-
-localhost:
- name : 'local'
- host : 'localhost'
- port : 11211
-
-localipv4:
- name : 'local'
- host : '127.0.0.1'
- port : 11211
-
-localipv6:
- name : 'local'
- host : '::1'
- port : 11211
-
diff --git a/src/collectors/python.d.plugin/python.d.conf b/src/collectors/python.d.plugin/python.d.conf
index 86e2ccc1bcaf57..7a3165b86a37d3 100644
--- a/src/collectors/python.d.plugin/python.d.conf
+++ b/src/collectors/python.d.plugin/python.d.conf
@@ -39,7 +39,6 @@ example: no
# gearman: yes
go_expvar: no
# haproxy: yes
-# memcached: yes
# monit: yes
# nvidia_smi: yes
# nsd: yes
@@ -74,6 +73,7 @@ icecast: no # Removed (replaced with go.d/icecast)
ipfs: no # Removed (replaced with go.d/ipfs).
litespeed: no # Removed (replaced with go.d/litespeed).
megacli: no # Removed (replaced with go.d/megacli).
+memcached: no # Removed (replaced with go.d/memcached).
mongodb: no # Removed (replaced with go.d/mongodb).
mysql: no # Removed (replaced with go.d/mysql).
nginx: no # Removed (replaced with go.d/nginx).
diff --git a/src/go/go.mod b/src/go/go.mod
index 0017f4d36cafc6..c1076a4848c69e 100644
--- a/src/go/go.mod
+++ b/src/go/go.mod
@@ -37,7 +37,6 @@ require (
github.com/mattn/go-xmlrpc v0.0.3
github.com/miekg/dns v1.1.61
github.com/mitchellh/go-homedir v1.1.0
- github.com/muesli/cancelreader v0.2.2
github.com/prometheus-community/pro-bing v0.4.0
github.com/prometheus/common v0.55.0
github.com/prometheus/prometheus v2.5.0+incompatible
diff --git a/src/go/go.sum b/src/go/go.sum
index 4380c17906213e..566c60083ec1b6 100644
--- a/src/go/go.sum
+++ b/src/go/go.sum
@@ -270,8 +270,6 @@ github.com/montanaflynn/stats v0.7.1 h1:etflOAAHORrCC44V+aR6Ftzort912ZU+YLiSTuV8
github.com/montanaflynn/stats v0.7.1/go.mod h1:etXPPgVO6n31NxCd9KQUMvCM+ve0ruNzt6R8Bnaayow=
github.com/morikuni/aec v1.0.0 h1:nP9CBfwrvYnBRgY6qfDQkygYDmYwOilePFkwzv4dU8A=
github.com/morikuni/aec v1.0.0/go.mod h1:BbKIizmSmc5MMPqRYbxO4ZU0S0+P200+tUnFx7PXmsc=
-github.com/muesli/cancelreader v0.2.2 h1:3I4Kt4BQjOR54NavqnDogx/MIoWBFa0StPA8ELUXHmA=
-github.com/muesli/cancelreader v0.2.2/go.mod h1:3XuTXfFS2VjM+HTLZY9Ak0l6eUKfijIfMUZ4EgX0QYo=
github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822 h1:C3w9PqII01/Oq1c1nUAm88MOHcQC9l5mIlSMApZMrHA=
github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822/go.mod h1:+n7T8mK8HuQTcFwEeznm/DIxMOiR9yIdICNftLE1DvQ=
github.com/nxadm/tail v1.4.8 h1:nPr65rt6Y5JFSKQO7qToXr7pePgD6Gwiw05lkbyAQTE=
diff --git a/src/go/plugin/go.d/README.md b/src/go/plugin/go.d/README.md
index d150e2d5cf380c..aaa02ab19f909f 100644
--- a/src/go/plugin/go.d/README.md
+++ b/src/go/plugin/go.d/README.md
@@ -95,6 +95,7 @@ see the appropriate collector readme.
| [logstash](https://github.com/netdata/netdata/tree/master/src/go/plugin/go.d/modules/logstash) | Logstash |
| [lvm](https://github.com/netdata/netdata/tree/master/src/go/plugin/go.d/modules/lvm) | LVM logical volumes |
| [megacli](https://github.com/netdata/netdata/tree/master/src/go/plugin/go.d/modules/megacli) | MegaCli Hardware Raid |
+| [memcached](https://github.com/netdata/netdata/tree/master/src/go/plugin/go.d/modules/memcached) | Memcached |
| [mongoDB](https://github.com/netdata/netdata/tree/master/src/go/plugin/go.d/modules/mongodb) | MongoDB |
| [mysql](https://github.com/netdata/netdata/tree/master/src/go/plugin/go.d/modules/mysql) | MySQL |
| [nginx](https://github.com/netdata/netdata/tree/master/src/go/plugin/go.d/modules/nginx) | NGINX |
diff --git a/src/go/plugin/go.d/agent/functions/function.go b/src/go/plugin/go.d/agent/functions/function.go
index b2fd42932d7f56..b65d3d713590d6 100644
--- a/src/go/plugin/go.d/agent/functions/function.go
+++ b/src/go/plugin/go.d/agent/functions/function.go
@@ -3,8 +3,8 @@
package functions
import (
- "bufio"
"bytes"
+ "context"
"encoding/csv"
"fmt"
"strconv"
@@ -67,22 +67,30 @@ func parseFunction(s string) (*Function, error) {
return fn, nil
}
-func parseFunctionWithPayload(s string, sc *bufio.Scanner) (*Function, error) {
+func parseFunctionWithPayload(ctx context.Context, s string, in input) (*Function, error) {
fn, err := parseFunction(s)
if err != nil {
return nil, err
}
- var n int
var buf bytes.Buffer
- for sc.Scan() && sc.Text() != "FUNCTION_PAYLOAD_END" {
- if n++; n > 1 {
- buf.WriteString("\n")
+
+ for {
+ select {
+ case <-ctx.Done():
+ return nil, nil
+ case line, ok := <-in.lines():
+ if !ok {
+ return nil, nil
+ }
+ if line == "FUNCTION_PAYLOAD_END" {
+ fn.Payload = append(fn.Payload, buf.Bytes()...)
+ return fn, nil
+ }
+ if buf.Len() > 0 {
+ buf.WriteString("\n")
+ }
+ buf.WriteString(line)
}
- buf.WriteString(sc.Text())
}
-
- fn.Payload = append(fn.Payload, buf.Bytes()...)
-
- return fn, nil
}
diff --git a/src/go/plugin/go.d/agent/functions/input.go b/src/go/plugin/go.d/agent/functions/input.go
new file mode 100644
index 00000000000000..cb50c54d0db17e
--- /dev/null
+++ b/src/go/plugin/go.d/agent/functions/input.go
@@ -0,0 +1,35 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+
+package functions
+
+import (
+ "bufio"
+ "os"
+)
+
+type input interface {
+ lines() chan string
+}
+
+var stdinInput = func() input {
+ r := &stdinReader{chLines: make(chan string)}
+ go r.run()
+ return r
+}()
+
+type stdinReader struct {
+ chLines chan string
+}
+
+func (in *stdinReader) run() {
+ sc := bufio.NewScanner(bufio.NewReader(os.Stdin))
+
+ for sc.Scan() {
+ text := sc.Text()
+ in.chLines <- text
+ }
+}
+
+func (in *stdinReader) lines() chan string {
+ return in.chLines
+}
diff --git a/src/go/plugin/go.d/agent/functions/manager.go b/src/go/plugin/go.d/agent/functions/manager.go
index a726e71f7d305b..b7cdecd6ac5f42 100644
--- a/src/go/plugin/go.d/agent/functions/manager.go
+++ b/src/go/plugin/go.d/agent/functions/manager.go
@@ -3,13 +3,10 @@
package functions
import (
- "bufio"
"context"
"encoding/json"
"fmt"
- "io"
"log/slog"
- "os"
"strconv"
"strings"
"sync"
@@ -18,20 +15,15 @@ import (
"github.com/netdata/netdata/go/plugins/logger"
"github.com/netdata/netdata/go/plugins/plugin/go.d/agent/netdataapi"
"github.com/netdata/netdata/go/plugins/plugin/go.d/agent/safewriter"
-
- "github.com/mattn/go-isatty"
- "github.com/muesli/cancelreader"
)
-var isTerminal = isatty.IsTerminal(os.Stdout.Fd()) || isatty.IsTerminal(os.Stdin.Fd())
-
func NewManager() *Manager {
return &Manager{
Logger: logger.New().With(
slog.String("component", "functions manager"),
),
- Input: os.Stdin,
api: netdataapi.New(safewriter.Stdout),
+ input: stdinInput,
mux: &sync.Mutex{},
FunctionRegistry: make(map[string]func(Function)),
}
@@ -40,8 +32,10 @@ func NewManager() *Manager {
type Manager struct {
*logger.Logger
- Input io.Reader
- api *netdataapi.API
+ api *netdataapi.API
+
+ input input
+
mux *sync.Mutex
FunctionRegistry map[string]func(Function)
}
@@ -50,68 +44,65 @@ func (m *Manager) Run(ctx context.Context) {
m.Info("instance is started")
defer func() { m.Info("instance is stopped") }()
- if !isTerminal {
- r, err := cancelreader.NewReader(m.Input)
- if err != nil {
- m.Errorf("fail to create cancel reader: %v", err)
- return
- }
-
- go func() { <-ctx.Done(); r.Cancel() }()
-
- var wg sync.WaitGroup
+ var wg sync.WaitGroup
- wg.Add(1)
- go func() { defer wg.Done(); m.run(r) }()
+ wg.Add(1)
+ go func() { defer wg.Done(); m.run(ctx) }()
- wg.Wait()
- _ = r.Close()
- }
+ wg.Wait()
<-ctx.Done()
}
-func (m *Manager) run(r io.Reader) {
- sc := bufio.NewScanner(r)
-
- for sc.Scan() {
- text := sc.Text()
-
- var fn *Function
- var err error
-
- // FIXME: if we are waiting for FUNCTION_PAYLOAD_END and a new FUNCTION* appears,
- // we need to discard the current one and switch to the new one
- switch {
- case strings.HasPrefix(text, "FUNCTION "):
- fn, err = parseFunction(text)
- case strings.HasPrefix(text, "FUNCTION_PAYLOAD "):
- fn, err = parseFunctionWithPayload(text, sc)
- case text == "":
- continue
- default:
- m.Warningf("unexpected line: '%s'", text)
- continue
- }
-
- if err != nil {
- m.Warningf("parse function: %v ('%s')", err, text)
- continue
- }
-
- function, ok := m.lookupFunction(fn.Name)
- if !ok {
- m.Infof("skipping execution of '%s': unregistered function", fn.Name)
- m.respf(fn, 501, "unregistered function: %s", fn.Name)
- continue
- }
- if function == nil {
- m.Warningf("skipping execution of '%s': nil function registered", fn.Name)
- m.respf(fn, 501, "nil function: %s", fn.Name)
- continue
+func (m *Manager) run(ctx context.Context) {
+ for {
+ select {
+ case <-ctx.Done():
+ return
+ case line, ok := <-m.input.lines():
+ if !ok {
+ return
+ }
+
+ var fn *Function
+ var err error
+
+ // FIXME: if we are waiting for FUNCTION_PAYLOAD_END and a new FUNCTION* appears,
+ // we need to discard the current one and switch to the new one
+ switch {
+ case strings.HasPrefix(line, "FUNCTION "):
+ fn, err = parseFunction(line)
+ case strings.HasPrefix(line, "FUNCTION_PAYLOAD "):
+ fn, err = parseFunctionWithPayload(ctx, line, m.input)
+ case line == "":
+ continue
+ default:
+ m.Warningf("unexpected line: '%s'", line)
+ continue
+ }
+
+ if err != nil {
+ m.Warningf("parse function: %v ('%s')", err, line)
+ continue
+ }
+ if fn == nil {
+ continue
+ }
+
+ function, ok := m.lookupFunction(fn.Name)
+ if !ok {
+ m.Infof("skipping execution of '%s': unregistered function", fn.Name)
+ m.respf(fn, 501, "unregistered function: %s", fn.Name)
+ continue
+ }
+ if function == nil {
+ m.Warningf("skipping execution of '%s': nil function registered", fn.Name)
+ m.respf(fn, 501, "nil function: %s", fn.Name)
+ continue
+ }
+
+ function(*fn)
}
-
- function(*fn)
}
}
diff --git a/src/go/plugin/go.d/agent/functions/manager_test.go b/src/go/plugin/go.d/agent/functions/manager_test.go
index 26a8cdd0c52858..c19519bc17a55a 100644
--- a/src/go/plugin/go.d/agent/functions/manager_test.go
+++ b/src/go/plugin/go.d/agent/functions/manager_test.go
@@ -3,6 +3,7 @@
package functions
import (
+ "bufio"
"context"
"sort"
"strings"
@@ -15,7 +16,7 @@ import (
func TestNewManager(t *testing.T) {
mgr := NewManager()
- assert.NotNilf(t, mgr.Input, "Input")
+ assert.NotNilf(t, mgr.input, "Input")
assert.NotNilf(t, mgr.FunctionRegistry, "FunctionRegistry")
}
@@ -261,7 +262,7 @@ FUNCTION_PAYLOAD_END
t.Run(name, func(t *testing.T) {
mgr := NewManager()
- mgr.Input = strings.NewReader(test.input)
+ mgr.input = newMockInput(test.input)
mock := &mockFunctionExecutor{}
for _, v := range test.register {
@@ -297,3 +298,23 @@ type mockFunctionExecutor struct {
func (m *mockFunctionExecutor) execute(fn Function) {
m.executed = append(m.executed, fn)
}
+
+func newMockInput(data string) *mockInput {
+ m := &mockInput{chLines: make(chan string)}
+ sc := bufio.NewScanner(strings.NewReader(data))
+ go func() {
+ for sc.Scan() {
+ m.chLines <- sc.Text()
+ }
+ close(m.chLines)
+ }()
+ return m
+}
+
+type mockInput struct {
+ chLines chan string
+}
+
+func (m *mockInput) lines() chan string {
+ return m.chLines
+}
diff --git a/src/go/plugin/go.d/config/go.d.conf b/src/go/plugin/go.d/config/go.d.conf
index a9af186ad6a62e..c7a3e2559b8366 100644
--- a/src/go/plugin/go.d/config/go.d.conf
+++ b/src/go/plugin/go.d/config/go.d.conf
@@ -59,6 +59,7 @@ modules:
# logstash: yes
# lvm: yes
# megacli: yes
+# memcached: yes
# mongodb: yes
# mysql: yes
# nginx: yes
diff --git a/src/go/plugin/go.d/config/go.d/memcached.conf b/src/go/plugin/go.d/config/go.d/memcached.conf
new file mode 100644
index 00000000000000..60603be287aa32
--- /dev/null
+++ b/src/go/plugin/go.d/config/go.d/memcached.conf
@@ -0,0 +1,6 @@
+## All available configuration options, their descriptions and default values:
+## https://github.com/netdata/netdata/tree/master/src/go/plugin/go.d/modules/memcached#readme
+
+#jobs:
+# - name: local
+# address: 127.0.0.1:11211
diff --git a/src/go/plugin/go.d/config/go.d/sd/docker.conf b/src/go/plugin/go.d/config/go.d/sd/docker.conf
index 9fd8c9c045f798..e2809858b6b7ca 100644
--- a/src/go/plugin/go.d/config/go.d/sd/docker.conf
+++ b/src/go/plugin/go.d/config/go.d/sd/docker.conf
@@ -42,6 +42,8 @@ classify:
expr: '{{ and (eq .PrivatePort "5001") (match "sp" .Image "ipfs/kubo ipfs/kubo:*") }}'
- tags: "lighttpd"
expr: '{{ match "sp" .Image "*/lighttpd */lighttpd:*" }}'
+ - tags: "memcached"
+ expr: '{{ or (eq .PrivatePort "11211") (match "sp" .Image "memcached memcached:* */memcached */memcached:*") }}'
- tags: "mongodb"
expr: '{{ or (eq .PrivatePort "27017") (match "sp" .Image "mongo mongo:* */mongodb */mongodb:* */mongodb-community-server */mongodb-community-server:*") }}'
- tags: "mysql"
@@ -129,6 +131,11 @@ compose:
module: lighttpd
name: docker_{{.Name}}
url: http://{{.Address}}/server-status?auto
+ - selector: "memcached"
+ template: |
+ module: memcached
+ name: docker_{{.Name}}
+ address: {{.Address}}
- selector: "mongodb"
template: |
module: mongodb
@@ -201,6 +208,6 @@ compose:
url: http://{{.Address}}/metrics
- selector: "zookeeper"
template: |
- module: vernemq
+ module: zookeeper
name: docker_{{.Name}}
address: {{.Address}}
diff --git a/src/go/plugin/go.d/config/go.d/sd/net_listeners.conf b/src/go/plugin/go.d/config/go.d/sd/net_listeners.conf
index 9ad930a6167657..9dd0e46468f5a3 100644
--- a/src/go/plugin/go.d/config/go.d/sd/net_listeners.conf
+++ b/src/go/plugin/go.d/config/go.d/sd/net_listeners.conf
@@ -70,6 +70,8 @@ classify:
expr: '{{ and (eq .Port "80" "8080") (eq .Comm "lighttpd") }}'
- tags: "logstash"
expr: '{{ and (eq .Port "9600") (glob .Cmdline "*logstash*") }}'
+ - tags: "memcached"
+ expr: '{{ or (eq .Port "11211") (eq .Comm "memcached") }}'
- tags: "mongodb"
expr: '{{ or (eq .Port "27017") (eq .Comm "mongod") }}'
- tags: "mysql"
@@ -293,6 +295,11 @@ compose:
module: logstash
name: local
url: http://{{.Address}}
+ - selector: "memcached"
+ template: |
+ module: memcached
+ name: local
+ address: {{.Address}}
- selector: "mongodb"
template: |
module: mongodb
diff --git a/src/go/plugin/go.d/modules/chrony/client.go b/src/go/plugin/go.d/modules/chrony/client.go
index 2c3ba84527c597..233e78f1944e6c 100644
--- a/src/go/plugin/go.d/modules/chrony/client.go
+++ b/src/go/plugin/go.d/modules/chrony/client.go
@@ -5,6 +5,7 @@ package chrony
import (
"fmt"
"net"
+ "time"
"github.com/facebook/time/ntp/chrony"
)
@@ -16,13 +17,39 @@ func newChronyClient(c Config) (chronyClient, error) {
}
client := &simpleClient{
- conn: conn,
- client: &chrony.Client{Connection: conn},
+ conn: conn,
+ client: &chrony.Client{Connection: &connWithTimeout{
+ Conn: conn,
+ timeout: c.Timeout.Duration(),
+ }},
}
return client, nil
}
+type connWithTimeout struct {
+ net.Conn
+ timeout time.Duration
+}
+
+func (c *connWithTimeout) Read(p []byte) (n int, err error) {
+ if err := c.Conn.SetReadDeadline(c.deadline()); err != nil {
+ return 0, err
+ }
+ return c.Conn.Read(p)
+}
+
+func (c *connWithTimeout) Write(p []byte) (n int, err error) {
+ if err := c.Conn.SetWriteDeadline(c.deadline()); err != nil {
+ return 0, err
+ }
+ return c.Conn.Write(p)
+}
+
+func (c *connWithTimeout) deadline() time.Time {
+ return time.Now().Add(c.timeout)
+}
+
type simpleClient struct {
conn net.Conn
client *chrony.Client
diff --git a/src/go/plugin/go.d/modules/init.go b/src/go/plugin/go.d/modules/init.go
index 0b00b81b108a7b..983eaf803cc9fb 100644
--- a/src/go/plugin/go.d/modules/init.go
+++ b/src/go/plugin/go.d/modules/init.go
@@ -50,6 +50,7 @@ import (
_ "github.com/netdata/netdata/go/plugins/plugin/go.d/modules/logstash"
_ "github.com/netdata/netdata/go/plugins/plugin/go.d/modules/lvm"
_ "github.com/netdata/netdata/go/plugins/plugin/go.d/modules/megacli"
+ _ "github.com/netdata/netdata/go/plugins/plugin/go.d/modules/memcached"
_ "github.com/netdata/netdata/go/plugins/plugin/go.d/modules/mongodb"
_ "github.com/netdata/netdata/go/plugins/plugin/go.d/modules/mysql"
_ "github.com/netdata/netdata/go/plugins/plugin/go.d/modules/nginx"
diff --git a/src/go/plugin/go.d/modules/megacli/integrations/megacli_megaraid.md b/src/go/plugin/go.d/modules/megacli/integrations/megacli_megaraid.md
index b7e7fc5ad04a28..54ec8bf50d0eed 100644
--- a/src/go/plugin/go.d/modules/megacli/integrations/megacli_megaraid.md
+++ b/src/go/plugin/go.d/modules/megacli/integrations/megacli_megaraid.md
@@ -113,8 +113,9 @@ Metrics:
| Metric | Dimensions | Unit |
|:------|:----------|:----|
-| megacli.bbu_relative_charge | charge | percentage |
+| megacli.bbu_charge | charge | percentage |
| megacli.bbu_recharge_cycles | recharge | cycles |
+| megacli.bbu_capacity_degradation | cap_degradation | percent |
| megacli.bbu_temperature | temperature | Celsius |
diff --git a/src/collectors/python.d.plugin/memcached/README.md b/src/go/plugin/go.d/modules/memcached/README.md
similarity index 100%
rename from src/collectors/python.d.plugin/memcached/README.md
rename to src/go/plugin/go.d/modules/memcached/README.md
diff --git a/src/go/plugin/go.d/modules/memcached/charts.go b/src/go/plugin/go.d/modules/memcached/charts.go
new file mode 100644
index 00000000000000..14cb1bf115282f
--- /dev/null
+++ b/src/go/plugin/go.d/modules/memcached/charts.go
@@ -0,0 +1,229 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+
+package memcached
+
+import (
+ "github.com/netdata/netdata/go/plugins/plugin/go.d/agent/module"
+)
+
+const (
+ prioCache = module.Priority + iota
+ prioNet
+ prioConnections
+ prioItems
+ prioEvictedReclaimed
+ prioGet
+ prioGetRate
+ prioSetRate
+ prioDelete
+ prioCas
+ prioIncrement
+ prioDecrement
+ prioTouch
+ prioTouchRate
+)
+
+var charts = module.Charts{
+ cacheChart.Copy(),
+ netChart.Copy(),
+ connectionsChart.Copy(),
+ itemsChart.Copy(),
+ EvictedReclaimedChart.Copy(),
+ getChart.Copy(),
+ getRateChart.Copy(),
+ setRateChart.Copy(),
+ deleteChart.Copy(),
+ casChart.Copy(),
+ incrementChart.Copy(),
+ decrementChart.Copy(),
+ touchChart.Copy(),
+ touchRateChart.Copy(),
+}
+
+const (
+ byteToMiB = 1 << 20
+)
+
+var (
+ cacheChart = module.Chart{
+ ID: "cache",
+ Title: "Cache Size",
+ Units: "MiB",
+ Fam: "cache",
+ Ctx: "memcached.cache",
+ Type: module.Stacked,
+ Priority: prioCache,
+ Dims: module.Dims{
+ {ID: "avail", Div: byteToMiB},
+ {ID: "bytes", Name: "used", Div: byteToMiB},
+ },
+ }
+ netChart = module.Chart{
+ ID: "net",
+ Title: "Network",
+ Units: "kilobits/s",
+ Fam: "network",
+ Ctx: "memcached.net",
+ Type: module.Area,
+ Priority: prioNet,
+ Dims: module.Dims{
+ {ID: "bytes_read", Name: "in", Mul: 8, Div: 1000, Algo: module.Incremental},
+ {ID: "bytes_written", Name: "out", Mul: -8, Div: 1000, Algo: module.Incremental},
+ },
+ }
+ connectionsChart = module.Chart{
+ ID: "connections",
+ Title: "Connections",
+ Units: "connections/s",
+ Fam: "connections",
+ Ctx: "memcached.connections",
+ Type: module.Line,
+ Priority: prioConnections,
+ Dims: module.Dims{
+ {ID: "curr_connections", Name: "current", Algo: module.Incremental},
+ {ID: "rejected_connections", Name: "rejected", Algo: module.Incremental},
+ {ID: "total_connections", Name: "total", Algo: module.Incremental},
+ },
+ }
+ itemsChart = module.Chart{
+ ID: "items",
+ Title: "Items",
+ Units: "items",
+ Fam: "items",
+ Ctx: "memcached.items",
+ Type: module.Line,
+ Priority: prioItems,
+ Dims: module.Dims{
+ {ID: "curr_items", Name: "current"},
+ {ID: "total_items", Name: "total"},
+ },
+ }
+ EvictedReclaimedChart = module.Chart{
+ ID: "evicted_reclaimed",
+ Title: "Evicted and Reclaimed Items",
+ Units: "items",
+ Fam: "items",
+ Ctx: "memcached.evicted_reclaimed",
+ Type: module.Line,
+ Priority: prioEvictedReclaimed,
+ Dims: module.Dims{
+ {ID: "reclaimed"},
+ {ID: "evictions", Name: "evicted"},
+ },
+ }
+ getChart = module.Chart{
+ ID: "get",
+ Title: "Get Requests",
+ Units: "requests",
+ Fam: "get ops",
+ Ctx: "memcached.get",
+ Type: module.Stacked,
+ Priority: prioGet,
+ Dims: module.Dims{
+ {ID: "get_hits", Name: "hits", Algo: module.PercentOfAbsolute},
+ {ID: "get_misses", Name: "misses", Algo: module.PercentOfAbsolute},
+ },
+ }
+ getRateChart = module.Chart{
+ ID: "get_rate",
+ Title: "Get Request Rate",
+ Units: "requests/s",
+ Fam: "get ops",
+ Ctx: "memcached.get_rate",
+ Type: module.Line,
+ Priority: prioGetRate,
+ Dims: module.Dims{
+ {ID: "cmd_get", Name: "rate", Algo: module.Incremental},
+ },
+ }
+ setRateChart = module.Chart{
+ ID: "set_rate",
+ Title: "Set Request Rate",
+ Units: "requests/s",
+ Fam: "set ops",
+ Ctx: "memcached.set_rate",
+ Type: module.Line,
+ Priority: prioSetRate,
+ Dims: module.Dims{
+ {ID: "cmd_set", Name: "rate", Algo: module.Incremental},
+ },
+ }
+ deleteChart = module.Chart{
+ ID: "delete",
+ Title: "Delete Requests",
+ Units: "requests",
+ Fam: "delete ops",
+ Ctx: "memcached.delete",
+ Type: module.Stacked,
+ Priority: prioDelete,
+ Dims: module.Dims{
+ {ID: "delete_hits", Name: "hits", Algo: module.PercentOfAbsolute},
+ {ID: "delete_misses", Name: "misses", Algo: module.PercentOfAbsolute},
+ },
+ }
+ casChart = module.Chart{
+ ID: "cas",
+ Title: "Check and Set Requests",
+ Units: "requests",
+ Fam: "check and set ops",
+ Ctx: "memcached.cas",
+ Type: module.Stacked,
+ Priority: prioCas,
+ Dims: module.Dims{
+ {ID: "cas_hits", Name: "hits", Algo: module.PercentOfAbsolute},
+ {ID: "cas_misses", Name: "misses", Algo: module.PercentOfAbsolute},
+ {ID: "cas_badval", Name: "bad value", Algo: module.PercentOfAbsolute},
+ },
+ }
+ incrementChart = module.Chart{
+ ID: "increment",
+ Title: "Increment Requests",
+ Units: "requests",
+ Fam: "increment ops",
+ Ctx: "memcached.increment",
+ Type: module.Stacked,
+ Priority: prioIncrement,
+ Dims: module.Dims{
+ {ID: "incr_hits", Name: "hits", Algo: module.PercentOfAbsolute},
+ {ID: "incr_misses", Name: "misses", Algo: module.PercentOfAbsolute},
+ },
+ }
+ decrementChart = module.Chart{
+ ID: "decrement",
+ Title: "Decrement Requests",
+ Units: "requests",
+ Fam: "decrement ops",
+ Ctx: "memcached.decrement",
+ Type: module.Stacked,
+ Priority: prioDecrement,
+ Dims: module.Dims{
+ {ID: "decr_hits", Name: "hits", Algo: module.PercentOfAbsolute},
+ {ID: "decr_misses", Name: "misses", Algo: module.PercentOfAbsolute},
+ },
+ }
+ touchChart = module.Chart{
+ ID: "touch",
+ Title: "Touch Requests",
+ Units: "requests",
+ Fam: "touch ops",
+ Ctx: "memcached.touch",
+ Type: module.Stacked,
+ Priority: prioTouch,
+ Dims: module.Dims{
+ {ID: "touch_hits", Name: "hits", Algo: module.PercentOfAbsolute},
+ {ID: "touch_misses", Name: "misses", Algo: module.PercentOfAbsolute},
+ },
+ }
+ touchRateChart = module.Chart{
+ ID: "touch_rate",
+ Title: "Touch Requests Rate",
+ Units: "requests/s",
+ Fam: "touch ops",
+ Ctx: "memcached.touch_rate",
+ Type: module.Line,
+ Priority: prioTouchRate,
+ Dims: module.Dims{
+ {ID: "cmd_touch", Name: "rate", Algo: module.Incremental},
+ },
+ }
+)
diff --git a/src/go/plugin/go.d/modules/memcached/client.go b/src/go/plugin/go.d/modules/memcached/client.go
new file mode 100644
index 00000000000000..679e3eb0feb7b3
--- /dev/null
+++ b/src/go/plugin/go.d/modules/memcached/client.go
@@ -0,0 +1,45 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+
+package memcached
+
+import (
+ "bytes"
+ "strings"
+
+ "github.com/netdata/netdata/go/plugins/plugin/go.d/pkg/socket"
+)
+
+func newMemcachedConn(conf Config) memcachedConn {
+ return &memcachedClient{conn: socket.New(socket.Config{
+ Address: conf.Address,
+ ConnectTimeout: conf.Timeout.Duration(),
+ ReadTimeout: conf.Timeout.Duration(),
+ WriteTimeout: conf.Timeout.Duration(),
+ })}
+}
+
+type memcachedClient struct {
+ conn socket.Client
+}
+
+func (c *memcachedClient) connect() error {
+ return c.conn.Connect()
+}
+
+func (c *memcachedClient) disconnect() {
+ _ = c.conn.Disconnect()
+}
+
+func (c *memcachedClient) queryStats() ([]byte, error) {
+ var b bytes.Buffer
+ err := c.conn.Command("stats\r\n", func(bytes []byte) bool {
+ s := strings.TrimSpace(string(bytes))
+ b.WriteString(s)
+ b.WriteByte('\n')
+ return !(strings.HasPrefix(s, "END") || strings.HasPrefix(s, "ERROR"))
+ })
+ if err != nil {
+ return nil, err
+ }
+ return b.Bytes(), nil
+}
diff --git a/src/go/plugin/go.d/modules/memcached/collect.go b/src/go/plugin/go.d/modules/memcached/collect.go
new file mode 100644
index 00000000000000..9ead8f47b2600d
--- /dev/null
+++ b/src/go/plugin/go.d/modules/memcached/collect.go
@@ -0,0 +1,121 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+
+package memcached
+
+import (
+ "bufio"
+ "bytes"
+ "errors"
+ "strconv"
+ "strings"
+)
+
+// https://github.com/memcached/memcached/blob/b1aefcdf8a265f8a5126e8aa107a50988fa1ec35/doc/protocol.txt#L1267
+var statsMetrics = map[string]bool{
+ "limit_maxbytes": true,
+ "bytes": true,
+ "bytes_read": true,
+ "bytes_written": true,
+ "cas_badval": true,
+ "cas_hits": true,
+ "cas_misses": true,
+ "cmd_get": true,
+ "cmd_set": true,
+ "cmd_touch": true,
+ "curr_connections": true,
+ "curr_items": true,
+ "decr_hits": true,
+ "decr_misses": true,
+ "delete_hits": true,
+ "delete_misses": true,
+ "evictions": true,
+ "get_hits": true,
+ "get_misses": true,
+ "incr_hits": true,
+ "incr_misses": true,
+ "reclaimed": true,
+ "rejected_connections": true,
+ "total_connections": true,
+ "total_items": true,
+ "touch_hits": true,
+ "touch_misses": true,
+}
+
+func (m *Memcached) collect() (map[string]int64, error) {
+ if m.conn == nil {
+ conn, err := m.establishConn()
+ if err != nil {
+ return nil, err
+ }
+ m.conn = conn
+ }
+
+ stats, err := m.conn.queryStats()
+ if err != nil {
+ m.conn.disconnect()
+ m.conn = nil
+ return nil, err
+ }
+
+ mx := make(map[string]int64)
+
+ if err := m.collectStats(mx, stats); err != nil {
+ return nil, err
+ }
+
+ return mx, nil
+}
+
+func (m *Memcached) collectStats(mx map[string]int64, stats []byte) error {
+ if len(stats) == 0 {
+ return errors.New("empty stats response")
+ }
+
+ var n int
+ sc := bufio.NewScanner(bytes.NewReader(stats))
+
+ for sc.Scan() {
+ line := strings.TrimSpace(sc.Text())
+
+ switch {
+ case strings.HasPrefix(line, "STAT"):
+ key, value := getStatKeyValue(line)
+ if !statsMetrics[key] {
+ continue
+ }
+ if v, err := strconv.ParseInt(value, 10, 64); err == nil {
+ mx[key] = v
+ n++
+ }
+ case strings.HasPrefix(line, "ERROR"):
+ return errors.New("received ERROR response")
+ }
+ }
+
+ if n == 0 {
+ return errors.New("unexpected memcached response")
+ }
+
+ mx["avail"] = mx["limit_maxbytes"] - mx["bytes"]
+
+ return nil
+}
+
+func (m *Memcached) establishConn() (memcachedConn, error) {
+ conn := m.newMemcachedConn(m.Config)
+
+ if err := conn.connect(); err != nil {
+ return nil, err
+ }
+
+ return conn, nil
+}
+
+func getStatKeyValue(line string) (string, string) {
+ line = strings.TrimPrefix(line, "STAT ")
+ i := strings.IndexByte(line, ' ')
+ if i < 0 {
+ return "", ""
+ }
+ return line[:i], line[i+1:]
+}
diff --git a/src/go/plugin/go.d/modules/memcached/config_schema.json b/src/go/plugin/go.d/modules/memcached/config_schema.json
new file mode 100644
index 00000000000000..f92a8eee919e64
--- /dev/null
+++ b/src/go/plugin/go.d/modules/memcached/config_schema.json
@@ -0,0 +1,44 @@
+{
+ "jsonSchema": {
+ "$schema": "http://json-schema.org/draft-07/schema#",
+ "title": "Memcached collector configuration.",
+ "type": "object",
+ "properties": {
+ "update_every": {
+ "title": "Update every",
+ "description": "Data collection interval, measured in seconds.",
+ "type": "integer",
+ "minimum": 1,
+ "default": 1
+ },
+ "address": {
+ "title": "Address",
+ "description": "The IP address and port where the memcached service listens for connections.",
+ "type": "string",
+ "default": "127.0.0.1:11211"
+ },
+ "timeout": {
+ "title": "Timeout",
+ "description": "Timeout for establishing a connection and communication (reading and writing) in seconds.",
+ "type": "number",
+ "minimum": 0.5,
+ "default": 1
+ }
+ },
+ "required": [
+ "address"
+ ],
+ "additionalProperties": false,
+ "patternProperties": {
+ "^name$": {}
+ }
+ },
+ "uiSchema": {
+ "uiOptions": {
+ "fullPage": true
+ },
+ "timeout": {
+ "ui:help": "Accepts decimals for precise control (e.g., type 1.5 for 1.5 seconds)."
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/collectors/python.d.plugin/memcached/integrations/memcached.md b/src/go/plugin/go.d/modules/memcached/integrations/memcached.md
similarity index 71%
rename from src/collectors/python.d.plugin/memcached/integrations/memcached.md
rename to src/go/plugin/go.d/modules/memcached/integrations/memcached.md
index 81765aaae0e481..87fd889db2d870 100644
--- a/src/collectors/python.d.plugin/memcached/integrations/memcached.md
+++ b/src/go/plugin/go.d/modules/memcached/integrations/memcached.md
@@ -1,6 +1,6 @@
-Plugin: python.d.plugin
+Plugin: go.d.plugin
Module: memcached
@@ -23,7 +23,7 @@ Module: memcached
Monitor Memcached metrics for proficient in-memory key-value store operations. Track cache hits, misses, and memory usage for efficient data caching.
-It reads server response to stats command ([stats interface](https://github.com/memcached/memcached/wiki/Commands#stats)).
+It reads the server's response to the `stats` command.
This collector is supported on all platforms.
@@ -103,7 +103,7 @@ No action required.
#### File
-The configuration file name for this integration is `python.d/memcached.conf`.
+The configuration file name for this integration is `go.d/memcached.conf`.
You can edit the configuration file using the `edit-config` script from the
@@ -111,75 +111,56 @@ Netdata [config directory](/docs/netdata-agent/configuration/README.md#the-netda
```bash
cd /etc/netdata 2>/dev/null || cd /opt/netdata/etc/netdata
-sudo ./edit-config python.d/memcached.conf
+sudo ./edit-config go.d/memcached.conf
```
#### Options
-There are 2 sections:
-
-* Global variables
-* One or more JOBS that can define multiple different instances to monitor.
-
-The following options can be defined globally: priority, penalty, autodetection_retry, update_every, but can also be defined per JOB to override the global values.
-
-Additionally, the following collapsed table contains all the options that can be configured inside a JOB definition.
-
-Every configuration JOB starts with a `job_name` value which will appear in the dashboard, unless a `name` parameter is specified.
+The following options can be defined globally: update_every, autodetection_retry.
Config options
| Name | Description | Default | Required |
|:----|:-----------|:-------|:--------:|
-| host | the host to connect to. | 127.0.0.1 | no |
-| port | the port to connect to. | 11211 | no |
-| update_every | Sets the default data collection frequency. | 10 | no |
-| priority | Controls the order of charts at the netdata dashboard. | 60000 | no |
-| autodetection_retry | Sets the job re-check interval in seconds. | 0 | no |
-| penalty | Indicates whether to apply penalty to update_every in case of failures. | yes | no |
-| name | Job name. This value will overwrite the `job_name` value. JOBS with the same name are mutually exclusive. Only one of them will be allowed running at any time. This allows autodetection to try several alternatives and pick the one that works. | | no |
+| update_every | Data collection frequency. | 1 | no |
+| autodetection_retry | Recheck interval in seconds. Zero means no recheck will be scheduled. | 0 | no |
+| address | The IP address and port where the memcached service listens for connections. | 127.0.0.1:11211 | yes |
+| timeout | Connection, read, and write timeout duration in seconds. The timeout includes name resolution. | 1 | no |
#### Examples
-##### localhost
-
-An example configuration for localhost.
-
-```yaml
-localhost:
- name: 'local'
- host: 'localhost'
- port: 11211
-
-```
-##### localipv4
+##### Basic
-An example configuration for localipv4.
+A basic example configuration.
Config
```yaml
-localhost:
- name: 'local'
- host: '127.0.0.1'
- port: 11211
+jobs:
+ - name: local
+ address: 127.0.0.1:11211
```
-##### localipv6
+##### Multi-instance
+
+> **Note**: When you define multiple jobs, their names must be unique.
+
+Collecting metrics from local and remote instances.
-An example configuration for localipv6.
Config
```yaml
-localhost:
- name: 'local'
- host: '::1'
- port: 11211
+jobs:
+ - name: local
+ address: 127.0.0.1:11211
+
+ - name: remote
+ address: 203.0.113.0:11211
```
@@ -190,7 +171,7 @@ localhost:
### Debug Mode
-To troubleshoot issues with the `memcached` collector, run the `python.d.plugin` with the debug option enabled. The output
+To troubleshoot issues with the `memcached` collector, run the `go.d.plugin` with the debug option enabled. The output
should give you clues as to why the collector isn't working.
- Navigate to the `plugins.d` directory, usually at `/usr/libexec/netdata/plugins.d/`. If that's not the case on
@@ -206,10 +187,10 @@ should give you clues as to why the collector isn't working.
sudo -u netdata -s
```
-- Run the `python.d.plugin` to debug the collector:
+- Run the `go.d.plugin` to debug the collector:
```bash
- ./python.d.plugin memcached debug trace
+ ./go.d.plugin -d -m memcached
```
### Getting Logs
diff --git a/src/go/plugin/go.d/modules/memcached/memcached.go b/src/go/plugin/go.d/modules/memcached/memcached.go
new file mode 100644
index 00000000000000..bd6039aee8c2c0
--- /dev/null
+++ b/src/go/plugin/go.d/modules/memcached/memcached.go
@@ -0,0 +1,108 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+
+package memcached
+
+import (
+ _ "embed"
+ "errors"
+ "time"
+
+ "github.com/netdata/netdata/go/plugins/plugin/go.d/agent/module"
+ "github.com/netdata/netdata/go/plugins/plugin/go.d/pkg/web"
+)
+
+//go:embed "config_schema.json"
+var configSchema string
+
+func init() {
+ module.Register("memcached", module.Creator{
+ JobConfigSchema: configSchema,
+ Create: func() module.Module { return New() },
+ Config: func() any { return &Config{} },
+ })
+}
+
+func New() *Memcached {
+ return &Memcached{
+ Config: Config{
+ Address: "127.0.0.1:11211",
+ Timeout: web.Duration(time.Second * 1),
+ },
+ newMemcachedConn: newMemcachedConn,
+ charts: charts.Copy(),
+ }
+}
+
+type Config struct {
+ UpdateEvery int `yaml:"update_every,omitempty" json:"update_every"`
+ Address string `yaml:"address" json:"address"`
+ Timeout web.Duration `yaml:"timeout" json:"timeout"`
+}
+
+type (
+ Memcached struct {
+ module.Base
+ Config `yaml:",inline" json:""`
+
+ charts *module.Charts
+
+ newMemcachedConn func(Config) memcachedConn
+ conn memcachedConn
+ }
+ memcachedConn interface {
+ connect() error
+ disconnect()
+ queryStats() ([]byte, error)
+ }
+)
+
+func (m *Memcached) Configuration() any {
+ return m.Config
+}
+
+func (m *Memcached) Init() error {
+ if m.Address == "" {
+ m.Error("config: 'address' not set")
+ return errors.New("address not set")
+ }
+
+ return nil
+}
+
+func (m *Memcached) Check() error {
+ mx, err := m.collect()
+ if err != nil {
+ m.Error(err)
+ return err
+ }
+
+ if len(mx) == 0 {
+ return errors.New("no metrics collected")
+ }
+
+ return nil
+}
+
+func (m *Memcached) Charts() *module.Charts {
+ return m.charts
+}
+
+func (m *Memcached) Collect() map[string]int64 {
+ mx, err := m.collect()
+ if err != nil {
+ m.Error(err)
+ }
+
+ if len(mx) == 0 {
+ return nil
+ }
+
+ return mx
+}
+
+func (m *Memcached) Cleanup() {
+ if m.conn != nil {
+ m.conn.disconnect()
+ m.conn = nil
+ }
+}
diff --git a/src/go/plugin/go.d/modules/memcached/memcached_test.go b/src/go/plugin/go.d/modules/memcached/memcached_test.go
new file mode 100644
index 00000000000000..33a85d3309fb21
--- /dev/null
+++ b/src/go/plugin/go.d/modules/memcached/memcached_test.go
@@ -0,0 +1,296 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+
+package memcached
+
+import (
+ "errors"
+ "os"
+ "testing"
+
+ "github.com/netdata/netdata/go/plugins/plugin/go.d/agent/module"
+
+ "github.com/stretchr/testify/assert"
+ "github.com/stretchr/testify/require"
+)
+
+var (
+ dataConfigJSON, _ = os.ReadFile("testdata/config.json")
+ dataConfigYAML, _ = os.ReadFile("testdata/config.yaml")
+
+ dataMemcachedStats, _ = os.ReadFile("testdata/stats.txt")
+)
+
+func Test_testDataIsValid(t *testing.T) {
+ for name, data := range map[string][]byte{
+ "dataConfigJSON": dataConfigJSON,
+ "dataConfigYAML": dataConfigYAML,
+
+ "dataMemcachedStats": dataMemcachedStats,
+ } {
+ require.NotNil(t, data, name)
+ }
+}
+
+func TestMemcached_ConfigurationSerialize(t *testing.T) {
+ module.TestConfigurationSerialize(t, &Memcached{}, dataConfigJSON, dataConfigYAML)
+}
+
+func TestMemcached_Init(t *testing.T) {
+ tests := map[string]struct {
+ config Config
+ wantFail bool
+ }{
+ "success with default config": {
+ wantFail: false,
+ config: New().Config,
+ },
+ "fails if address not set": {
+ wantFail: true,
+ config: func() Config {
+ conf := New().Config
+ conf.Address = ""
+ return conf
+ }(),
+ },
+ }
+
+ for name, test := range tests {
+ t.Run(name, func(t *testing.T) {
+ mem := New()
+ mem.Config = test.config
+
+ if test.wantFail {
+ assert.Error(t, mem.Init())
+ } else {
+ assert.NoError(t, mem.Init())
+ }
+ })
+ }
+}
+
+func TestMemcached_Cleanup(t *testing.T) {
+ tests := map[string]struct {
+ prepare func() *Memcached
+ }{
+ "not initialized": {
+ prepare: func() *Memcached {
+ return New()
+ },
+ },
+ "after check": {
+ prepare: func() *Memcached {
+ mem := New()
+ mem.newMemcachedConn = func(config Config) memcachedConn { return prepareMockOk() }
+ _ = mem.Check()
+ return mem
+ },
+ },
+ "after collect": {
+ prepare: func() *Memcached {
+ mem := New()
+ mem.newMemcachedConn = func(config Config) memcachedConn { return prepareMockOk() }
+ _ = mem.Collect()
+ return mem
+ },
+ },
+ }
+
+ for name, test := range tests {
+ t.Run(name, func(t *testing.T) {
+ mem := test.prepare()
+
+ assert.NotPanics(t, mem.Cleanup)
+ })
+ }
+}
+
+func TestMemcached_Charts(t *testing.T) {
+ assert.NotNil(t, New().Charts())
+}
+
+func TestMemcached_Check(t *testing.T) {
+ tests := map[string]struct {
+ prepareMock func() *mockMemcachedConn
+ wantFail bool
+ }{
+ "success case": {
+ wantFail: false,
+ prepareMock: prepareMockOk,
+ },
+ "err on connect": {
+ wantFail: true,
+ prepareMock: prepareMockErrOnConnect,
+ },
+ "unexpected response": {
+ wantFail: true,
+ prepareMock: prepareMockUnexpectedResponse,
+ },
+ "empty response": {
+ wantFail: true,
+ prepareMock: prepareMockEmptyResponse,
+ },
+ }
+
+ for name, test := range tests {
+ t.Run(name, func(t *testing.T) {
+ mem := New()
+ mock := test.prepareMock()
+ mem.newMemcachedConn = func(config Config) memcachedConn { return mock }
+
+ if test.wantFail {
+ assert.Error(t, mem.Check())
+ } else {
+ assert.NoError(t, mem.Check())
+ }
+ })
+ }
+}
+
+func TestMemcached_Collect(t *testing.T) {
+ tests := map[string]struct {
+ prepareMock func() *mockMemcachedConn
+ wantMetrics map[string]int64
+ disconnectBeforeCleanup bool
+ disconnectAfterCleanup bool
+ }{
+ "success case": {
+ prepareMock: prepareMockOk,
+ disconnectBeforeCleanup: false,
+ disconnectAfterCleanup: true,
+ wantMetrics: map[string]int64{
+ "avail": 67108831,
+ "bytes": 33,
+ "bytes_read": 108662,
+ "bytes_written": 9761348,
+ "cas_badval": 0,
+ "cas_hits": 0,
+ "cas_misses": 0,
+ "cmd_get": 1,
+ "cmd_set": 1,
+ "cmd_touch": 0,
+ "curr_connections": 3,
+ "curr_items": 0,
+ "decr_hits": 0,
+ "decr_misses": 0,
+ "delete_hits": 0,
+ "delete_misses": 0,
+ "evictions": 0,
+ "get_hits": 0,
+ "get_misses": 1,
+ "incr_hits": 0,
+ "incr_misses": 0,
+ "limit_maxbytes": 67108864,
+ "reclaimed": 1,
+ "rejected_connections": 0,
+ "total_connections": 39,
+ "total_items": 1,
+ "touch_hits": 0,
+ "touch_misses": 0,
+ },
+ },
+ "error response": {
+ prepareMock: prepareMockErrorResponse,
+ disconnectBeforeCleanup: false,
+ disconnectAfterCleanup: true,
+ },
+ "unexpected response": {
+ prepareMock: prepareMockUnexpectedResponse,
+ disconnectBeforeCleanup: false,
+ disconnectAfterCleanup: true,
+ },
+ "empty response": {
+ prepareMock: prepareMockEmptyResponse,
+ disconnectBeforeCleanup: false,
+ disconnectAfterCleanup: true,
+ },
+ "err on connect": {
+ prepareMock: prepareMockErrOnConnect,
+ disconnectBeforeCleanup: false,
+ disconnectAfterCleanup: false,
+ },
+ "err on query stats": {
+ prepareMock: prepareMockErrOnQueryStats,
+ disconnectBeforeCleanup: true,
+ disconnectAfterCleanup: true,
+ },
+ }
+
+ for name, test := range tests {
+ t.Run(name, func(t *testing.T) {
+ mem := New()
+ mock := test.prepareMock()
+ mem.newMemcachedConn = func(config Config) memcachedConn { return mock }
+
+ mx := mem.Collect()
+
+ require.Equal(t, test.wantMetrics, mx)
+
+ if len(test.wantMetrics) > 0 {
+ module.TestMetricsHasAllChartsDims(t, mem.Charts(), mx)
+ }
+
+ assert.Equal(t, test.disconnectBeforeCleanup, mock.disconnectCalled, "disconnect before cleanup")
+ mem.Cleanup()
+ assert.Equal(t, test.disconnectAfterCleanup, mock.disconnectCalled, "disconnect after cleanup")
+ })
+ }
+}
+
+func prepareMockOk() *mockMemcachedConn {
+ return &mockMemcachedConn{
+ statsResponse: dataMemcachedStats,
+ }
+}
+
+func prepareMockErrorResponse() *mockMemcachedConn {
+ return &mockMemcachedConn{
+ statsResponse: []byte("ERROR"),
+ }
+}
+
+func prepareMockErrOnConnect() *mockMemcachedConn {
+ return &mockMemcachedConn{
+ errOnConnect: true,
+ }
+}
+
+func prepareMockErrOnQueryStats() *mockMemcachedConn {
+ return &mockMemcachedConn{
+ errOnQueryStats: true,
+ }
+}
+
+func prepareMockUnexpectedResponse() *mockMemcachedConn {
+ return &mockMemcachedConn{
+ statsResponse: []byte("Lorem ipsum dolor sit amet, consectetur adipiscing elit."),
+ }
+}
+
+func prepareMockEmptyResponse() *mockMemcachedConn {
+ return &mockMemcachedConn{}
+}
+
+type mockMemcachedConn struct {
+ errOnConnect bool
+ errOnQueryStats bool
+ statsResponse []byte
+ disconnectCalled bool
+}
+
+func (m *mockMemcachedConn) connect() error {
+ if m.errOnConnect {
+ return errors.New("mock.connect() error")
+ }
+ return nil
+}
+
+func (m *mockMemcachedConn) disconnect() {
+ m.disconnectCalled = true
+}
+
+func (m *mockMemcachedConn) queryStats() ([]byte, error) {
+ if m.errOnQueryStats {
+ return nil, errors.New("mock.queryStats() error")
+ }
+ return m.statsResponse, nil
+}
diff --git a/src/collectors/python.d.plugin/memcached/metadata.yaml b/src/go/plugin/go.d/modules/memcached/metadata.yaml
similarity index 67%
rename from src/collectors/python.d.plugin/memcached/metadata.yaml
rename to src/go/plugin/go.d/modules/memcached/metadata.yaml
index ae420f1c1dcdcf..c307ef0181cc51 100644
--- a/src/collectors/python.d.plugin/memcached/metadata.yaml
+++ b/src/go/plugin/go.d/modules/memcached/metadata.yaml
@@ -1,7 +1,8 @@
-plugin_name: python.d.plugin
+plugin_name: go.d.plugin
modules:
- meta:
- plugin_name: python.d.plugin
+ id: collector-go.d.plugin-memcached
+ plugin_name: go.d.plugin
module_name: memcached
monitored_instance:
name: Memcached
@@ -23,7 +24,7 @@ modules:
overview:
data_collection:
metrics_description: "Monitor Memcached metrics for proficient in-memory key-value store operations. Track cache hits, misses, and memory usage for efficient data caching."
- method_description: "It reads server response to stats command ([stats interface](https://github.com/memcached/memcached/wiki/Commands#stats))."
+ method_description: "It reads the server's response to the `stats` command."
supported_platforms:
include: []
exclude: []
@@ -43,84 +44,53 @@ modules:
list: []
configuration:
file:
- name: python.d/memcached.conf
- description: ""
+ name: go.d/memcached.conf
options:
description: |
- There are 2 sections:
-
- * Global variables
- * One or more JOBS that can define multiple different instances to monitor.
-
- The following options can be defined globally: priority, penalty, autodetection_retry, update_every, but can also be defined per JOB to override the global values.
-
- Additionally, the following collapsed table contains all the options that can be configured inside a JOB definition.
-
- Every configuration JOB starts with a `job_name` value which will appear in the dashboard, unless a `name` parameter is specified.
+ The following options can be defined globally: update_every, autodetection_retry.
folding:
title: Config options
enabled: true
list:
- - name: host
- description: the host to connect to.
- default_value: "127.0.0.1"
- required: false
- - name: port
- description: the port to connect to.
- default_value: "11211"
- required: false
- name: update_every
- description: Sets the default data collection frequency.
- default_value: 10
- required: false
- - name: priority
- description: Controls the order of charts at the netdata dashboard.
- default_value: 60000
+ description: Data collection frequency.
+ default_value: 1
required: false
- name: autodetection_retry
- description: Sets the job re-check interval in seconds.
+ description: Recheck interval in seconds. Zero means no recheck will be scheduled.
default_value: 0
required: false
- - name: penalty
- description: Indicates whether to apply penalty to update_every in case of failures.
- default_value: yes
- required: false
- - name: name
- description: Job name. This value will overwrite the `job_name` value. JOBS with the same name are mutually exclusive. Only one of them will be allowed running at any time. This allows autodetection to try several alternatives and pick the one that works.
- default_value: ""
+ - name: address
+ description: The IP address and port where the memcached service listens for connections.
+ default_value: 127.0.0.1:11211
+ required: true
+ - name: timeout
+ description: Connection, read, and write timeout duration in seconds. The timeout includes name resolution.
+ default_value: 1
required: false
examples:
folding:
+ title: Config
enabled: true
- title: "Config"
list:
- - name: localhost
- description: An example configuration for localhost.
- folding:
- enabled: false
- config: |
- localhost:
- name: 'local'
- host: 'localhost'
- port: 11211
- - name: localipv4
- description: An example configuration for localipv4.
- folding:
- enabled: true
+ - name: Basic
+ description: A basic example configuration.
config: |
- localhost:
- name: 'local'
- host: '127.0.0.1'
- port: 11211
- - name: localipv6
- description: An example configuration for localipv6.
- folding:
- enabled: true
+ jobs:
+ - name: local
+ address: 127.0.0.1:11211
+ - name: Multi-instance
+ description: |
+ > **Note**: When you define multiple jobs, their names must be unique.
+
+ Collecting metrics from local and remote instances.
config: |
- localhost:
- name: 'local'
- host: '::1'
- port: 11211
+ jobs:
+ - name: local
+ address: 127.0.0.1:11211
+
+ - name: remote
+ address: 203.0.113.0:11211
troubleshooting:
problems:
list: []
diff --git a/src/go/plugin/go.d/modules/memcached/testdata/config.json b/src/go/plugin/go.d/modules/memcached/testdata/config.json
new file mode 100644
index 00000000000000..e868347203bee3
--- /dev/null
+++ b/src/go/plugin/go.d/modules/memcached/testdata/config.json
@@ -0,0 +1,5 @@
+{
+ "update_every": 123,
+ "address": "ok",
+ "timeout": 123.123
+}
diff --git a/src/go/plugin/go.d/modules/memcached/testdata/config.yaml b/src/go/plugin/go.d/modules/memcached/testdata/config.yaml
new file mode 100644
index 00000000000000..1b81d09eb8288b
--- /dev/null
+++ b/src/go/plugin/go.d/modules/memcached/testdata/config.yaml
@@ -0,0 +1,3 @@
+update_every: 123
+address: "ok"
+timeout: 123.123
diff --git a/src/go/plugin/go.d/modules/memcached/testdata/stats.txt b/src/go/plugin/go.d/modules/memcached/testdata/stats.txt
new file mode 100644
index 00000000000000..b9647cc1d762fc
--- /dev/null
+++ b/src/go/plugin/go.d/modules/memcached/testdata/stats.txt
@@ -0,0 +1,93 @@
+STAT pid 30783
+STAT uptime 5028
+STAT time 1721297802
+STAT version 1.6.24
+STAT libevent 2.1.12-stable
+STAT pointer_size 64
+STAT rusage_user 1.026626
+STAT rusage_system 0.685365
+STAT max_connections 1024
+STAT curr_connections 3
+STAT total_connections 39
+STAT rejected_connections 0
+STAT connection_structures 6
+STAT response_obj_oom 0
+STAT response_obj_count 1
+STAT response_obj_bytes 65536
+STAT read_buf_count 9
+STAT read_buf_bytes 147456
+STAT read_buf_bytes_free 65536
+STAT read_buf_oom 0
+STAT reserved_fds 20
+STAT cmd_get 1
+STAT cmd_set 1
+STAT cmd_flush 0
+STAT cmd_touch 0
+STAT cmd_meta 0
+STAT get_hits 0
+STAT get_misses 1
+STAT get_expired 0
+STAT get_flushed 0
+STAT delete_misses 0
+STAT delete_hits 0
+STAT incr_misses 0
+STAT incr_hits 0
+STAT decr_misses 0
+STAT decr_hits 0
+STAT cas_misses 0
+STAT cas_hits 0
+STAT cas_badval 0
+STAT touch_hits 0
+STAT touch_misses 0
+STAT store_too_large 0
+STAT store_no_memory 0
+STAT auth_cmds 0
+STAT auth_errors 0
+STAT bytes_read 108662
+STAT bytes_written 9761348
+STAT limit_maxbytes 67108864
+STAT accepting_conns 1
+STAT listen_disabled_num 0
+STAT time_in_listen_disabled_us 0
+STAT threads 4
+STAT conn_yields 0
+STAT hash_power_level 16
+STAT hash_bytes 524288
+STAT hash_is_expanding 0
+STAT slab_reassign_rescues 0
+STAT slab_reassign_chunk_rescues 0
+STAT slab_reassign_evictions_nomem 0
+STAT slab_reassign_inline_reclaim 0
+STAT slab_reassign_busy_items 0
+STAT slab_reassign_busy_deletes 0
+STAT slab_reassign_running 0
+STAT slabs_moved 0
+STAT lru_crawler_running 0
+STAT lru_crawler_starts 13
+STAT lru_maintainer_juggles 9280
+STAT malloc_fails 0
+STAT log_worker_dropped 0
+STAT log_worker_written 0
+STAT log_watcher_skipped 0
+STAT log_watcher_sent 0
+STAT log_watchers 0
+STAT unexpected_napi_ids 0
+STAT round_robin_fallback 0
+STAT bytes 33
+STAT curr_items 0
+STAT total_items 1
+STAT slab_global_page_pool 0
+STAT expired_unfetched 1
+STAT evicted_unfetched 0
+STAT evicted_active 0
+STAT evictions 0
+STAT reclaimed 1
+STAT crawler_reclaimed 0
+STAT crawler_items_checked 0
+STAT lrutail_reflocked 0
+STAT moves_to_cold 1
+STAT moves_to_warm 0
+STAT moves_within_lru 0
+STAT direct_reclaims 0
+STAT lru_bumps_dropped 0
+END