From 5cfc9b1bd83e059b8de7c47fafea621a3ce6f294 Mon Sep 17 00:00:00 2001 From: Alberto Caravaca <3170731+albcp@users.noreply.github.com> Date: Fri, 20 Jan 2023 15:02:55 -0600 Subject: [PATCH 1/2] Added authentication to Pi-Hole widgets --- docs/widgets.md | 12 ++++++++---- src/components/Widgets/PiHoleStats.vue | 12 ++++++++++-- src/components/Widgets/PiHoleTraffic.vue | 10 ++++++++-- 3 files changed, 26 insertions(+), 8 deletions(-) diff --git a/docs/widgets.md b/docs/widgets.md index 4a1d6551..06656718 100644 --- a/docs/widgets.md +++ b/docs/widgets.md @@ -43,7 +43,7 @@ Dashy has support for displaying dynamic content in the form of widgets. There a - [System Load History](#load-history-netdata) - [Pi Hole Stats](#pi-hole-stats) - [Pi Hole Queries](#pi-hole-queries) - - [Recent Traffic](#recent-traffic) + - [Pi Hole Recent Traffic](#pi-hole-recent-traffic) - [Stat Ping Statuses](#stat-ping-statuses) - [Synology Download Station](#synology-download-station) - [AdGuard Home Block Stats](#adguard-home-block-stats) @@ -1338,6 +1338,7 @@ Displays the number of queries blocked by [Pi-Hole](https://pi-hole.net/). --- | --- | --- | --- **`hostname`** | `string` | Required | The URL to your Pi-Hole instance **`hideStatus`** / **`hideChart`** / **`hideInfo`** | `boolean` | _Optional_ | Optionally hide any of the three parts of the widget +**`apiKey`** | `string` | Required | Your Pi-Hole web password. It is **NOT** your pi-hole admin interface or server password. It can be found in `/etc/pihole/setupVars.conf`, and is a 64-character located on the line that starts with `WEBPASSWORD` #### Example @@ -1345,12 +1346,13 @@ Displays the number of queries blocked by [Pi-Hole](https://pi-hole.net/). - type: pi-hole-stats options: hostname: http://192.168.130.1 + apiKey: xxxxxxxxxxxxxxxxxxxxxxx ``` #### Info - **CORS**: 🟢 Enabled -- **Auth**: 🟢 Not Required +- **Auth**: 🔴 Required - **Price**: 🟢 Free - **Host**: Self-Hosted (see [GitHub - Pi-hole](https://github.com/pi-hole/pi-hole)) - **Privacy**: _See [Pi-Hole Privacy Guide](https://pi-hole.net/privacy/)_ @@ -1390,7 +1392,7 @@ Shows top queries that were blocked and allowed by [Pi-Hole](https://pi-hole.net --- -### Recent Traffic +### Pi Hole Recent Traffic Shows number of recent traffic, using allowed and blocked queries from [Pi-Hole](https://pi-hole.net/) @@ -1401,6 +1403,7 @@ Shows number of recent traffic, using allowed and blocked queries from [Pi-Hole] **Field** | **Type** | **Required** | **Description** --- | --- | --- | --- **`hostname`** | `string` | Required | The URL to your Pi-Hole instance +**`apiKey`** | `string` | Required | Your Pi-Hole web password. It is **NOT** your pi-hole admin interface or server password. It can be found in `/etc/pihole/setupVars.conf`, and is a 64-character located on the line that starts with `WEBPASSWORD` #### Example @@ -1408,12 +1411,13 @@ Shows number of recent traffic, using allowed and blocked queries from [Pi-Hole] - type: pi-hole-traffic options: hostname: https://pi-hole.local + apiKey: xxxxxxxxxxxxxxxxxxxxxxx ``` #### Info - **CORS**: 🟢 Enabled -- **Auth**: 🟢 Not Required +- **Auth**: 🔴 Required - **Price**: 🟢 Free - **Host**: Self-Hosted (see [GitHub - Pi-hole](https://github.com/pi-hole/pi-hole)) - **Privacy**: _See [Pi-Hole Privacy Guide](https://pi-hole.net/privacy/)_ diff --git a/src/components/Widgets/PiHoleStats.vue b/src/components/Widgets/PiHoleStats.vue index 2cd36897..ff909b7d 100644 --- a/src/components/Widgets/PiHoleStats.vue +++ b/src/components/Widgets/PiHoleStats.vue @@ -40,8 +40,12 @@ export default { if (!usersChoice) this.error('You must specify the hostname for your Pi-Hole server'); return usersChoice || 'http://pi.hole'; }, + apiKey() { + if (!this.options.apiKey) this.error('API Key is required, please see the docs'); + return this.options.apiKey; + }, endpoint() { - return `${this.hostname}/admin/api.php`; + return `${this.hostname}/admin/api.php?summary&auth=${this.apiKey}`; }, hideStatus() { return this.options.hideStatus; }, hideChart() { return this.options.hideChart; }, @@ -57,7 +61,11 @@ export default { fetchData() { this.makeRequest(this.endpoint) .then((response) => { - this.processData(response); + if (Array.isArray(response)) { + this.error('Got success, but found no results, possible authorization error'); + } else { + this.processData(response); + } }); }, /* Assign data variables to the returned data */ diff --git a/src/components/Widgets/PiHoleTraffic.vue b/src/components/Widgets/PiHoleTraffic.vue index a2de61d1..fdf16745 100644 --- a/src/components/Widgets/PiHoleTraffic.vue +++ b/src/components/Widgets/PiHoleTraffic.vue @@ -23,8 +23,12 @@ export default { if (!usersChoice) this.error('You must specify the hostname for your Pi-Hole server'); return usersChoice || 'http://pi.hole'; }, + apiKey() { + if (!this.options.apiKey) this.error('API Key is required, please see the docs'); + return this.options.apiKey; + }, endpoint() { - return `${this.hostname}/admin/api.php?overTimeData10mins`; + return `${this.hostname}/admin/api.php?overTimeData10mins&auth=${this.apiKey}`; }, }, methods: { @@ -38,7 +42,9 @@ export default { }); }, validate(response) { - if (!response.ads_over_time || !response.domains_over_time) { + if (Array.isArray(response)) { + this.error('Got success, but found no results, possible authorization error'); + } else if (!response.ads_over_time || !response.domains_over_time) { this.error('Expected data was not returned from Pi-Hole'); return false; } else if (response.ads_over_time.length < 1) { From c867a90919c0a12207baf601c36262e5b29918b3 Mon Sep 17 00:00:00 2001 From: Alberto Caravaca <3170731+albcp@users.noreply.github.com> Date: Fri, 20 Jan 2023 15:21:55 -0600 Subject: [PATCH 2/2] Remove trailing space --- src/components/Widgets/PiHoleTraffic.vue | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/components/Widgets/PiHoleTraffic.vue b/src/components/Widgets/PiHoleTraffic.vue index fdf16745..e51b011d 100644 --- a/src/components/Widgets/PiHoleTraffic.vue +++ b/src/components/Widgets/PiHoleTraffic.vue @@ -42,7 +42,7 @@ export default { }); }, validate(response) { - if (Array.isArray(response)) { + if (Array.isArray(response)) { this.error('Got success, but found no results, possible authorization error'); } else if (!response.ads_over_time || !response.domains_over_time) { this.error('Expected data was not returned from Pi-Hole');