From 291b28e4e8809dfacc870f03e65ac4b2f304342a Mon Sep 17 00:00:00 2001 From: richbenwell Date: Sun, 8 Feb 2026 22:11:04 -0500 Subject: [PATCH 1/8] OpenSearch plugin - initial commit --- plugins/OpenSearch/v1/README.md | 6 ++ .../OpenSearch/v1/dataStreams/indices.json | 28 +++++++++ .../v1/dataStreams/scripts/search.js | 32 ++++++++++ plugins/OpenSearch/v1/dataStreams/search.json | 50 ++++++++++++++++ plugins/OpenSearch/v1/docs/setup.md | 0 plugins/OpenSearch/v1/icon.svg | 6 ++ plugins/OpenSearch/v1/metadata.json | 33 ++++++++++ plugins/OpenSearch/v1/ui.json | 60 +++++++++++++++++++ 8 files changed, 215 insertions(+) create mode 100644 plugins/OpenSearch/v1/README.md create mode 100644 plugins/OpenSearch/v1/dataStreams/indices.json create mode 100644 plugins/OpenSearch/v1/dataStreams/scripts/search.js create mode 100644 plugins/OpenSearch/v1/dataStreams/search.json create mode 100644 plugins/OpenSearch/v1/docs/setup.md create mode 100644 plugins/OpenSearch/v1/icon.svg create mode 100644 plugins/OpenSearch/v1/metadata.json create mode 100644 plugins/OpenSearch/v1/ui.json diff --git a/plugins/OpenSearch/v1/README.md b/plugins/OpenSearch/v1/README.md new file mode 100644 index 0000000..374021e --- /dev/null +++ b/plugins/OpenSearch/v1/README.md @@ -0,0 +1,6 @@ +## Overview + +Query OpenSearch databases. This plugin is primarily a wrapper around the `_search` API endpoint that allows for a range of queries. + +See the [OpenSearch API docs](https://docs.opensearch.org/latest/api-reference/search-apis/search/) for more information. + diff --git a/plugins/OpenSearch/v1/dataStreams/indices.json b/plugins/OpenSearch/v1/dataStreams/indices.json new file mode 100644 index 0000000..b41f905 --- /dev/null +++ b/plugins/OpenSearch/v1/dataStreams/indices.json @@ -0,0 +1,28 @@ +{ + "name": "indices", + "displayName": "Indices", + "baseDataSourceName": "httpRequestUnscoped", + "config": { + "httpMethod": "get", + "pagingConfig_mode": "none", + "pagingConfig_offset_base": 1, + "expandInnerObjects": true, + "endpointPath": "_cat/indices", + "pathToData": "", + "getArgs": [], + "headers": [] + }, + "timeframes": false, + "matches": "none", + "options": { + "noMatch": true + }, + "metadata": [ + { + "name": "index", + "shape": "string", + "displayName": "Index", + "role": "value" + } + ] +} \ No newline at end of file diff --git a/plugins/OpenSearch/v1/dataStreams/scripts/search.js b/plugins/OpenSearch/v1/dataStreams/scripts/search.js new file mode 100644 index 0000000..ea8bc45 --- /dev/null +++ b/plugins/OpenSearch/v1/dataStreams/scripts/search.js @@ -0,0 +1,32 @@ +if (data.aggregations) { + + const agg = data.aggregations[Object.keys(data.aggregations).at(-1)]; // last aggregation to support pipelining + + if(agg.buckets) { + + result = agg.buckets; + + } else if (agg.values) { + + result = [agg.values]; + + } else if (agg.value) { + + result = [{ + value: agg.value + }]; + + } else { + + result = [agg]; + + } + +} else { + + result = data.hits.hits.map(hit => hit._source); + +} + + + diff --git a/plugins/OpenSearch/v1/dataStreams/search.json b/plugins/OpenSearch/v1/dataStreams/search.json new file mode 100644 index 0000000..c1dd8e3 --- /dev/null +++ b/plugins/OpenSearch/v1/dataStreams/search.json @@ -0,0 +1,50 @@ +{ + "name": "search", + "displayName": "Search", + "baseDataSourceName": "httpRequestUnscoped", + "matches": "none", + "manualConfigApply": true, + "config": { + "httpMethod": "post", + "pagingConfig_mode": "none", + "pagingConfig_offset_base": 1, + "expandInnerObjects": true, + "endpointPath": "{{index}}/_search", + "postRequestScript": "search.js", + "getArgs": [], + "headers": [], + "postBody": "{{query}}" + }, + "ui": [ + { + "name": "index", + "type": "autocomplete", + "label": "Index", + "validation": { + "required": true + }, + "placeholder": "Select index", + "isMulti": false, + "allowCustomValues": true, + "data": { + "source": "dataStream", + "dataStreamName": "indices" + } + }, + { + "name": "query", + "type": "json", + "defaultValue": { + "size": 100 + }, + "label": "Query body", + "help": "The Query DSL JSON. See [OpenSearch API docs](https://docs.opensearch.org/latest/api-reference/search-apis/search/#request-body).", + "validation": { + "required": true + } + } + ], + "supportsNoneTimeframe": true, + "requiresParameterTimeframe": true, + "defaultTimeframe": "none" +} \ No newline at end of file diff --git a/plugins/OpenSearch/v1/docs/setup.md b/plugins/OpenSearch/v1/docs/setup.md new file mode 100644 index 0000000..e69de29 diff --git a/plugins/OpenSearch/v1/icon.svg b/plugins/OpenSearch/v1/icon.svg new file mode 100644 index 0000000..65bc2fe --- /dev/null +++ b/plugins/OpenSearch/v1/icon.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/plugins/OpenSearch/v1/metadata.json b/plugins/OpenSearch/v1/metadata.json new file mode 100644 index 0000000..1f9cfe7 --- /dev/null +++ b/plugins/OpenSearch/v1/metadata.json @@ -0,0 +1,33 @@ +{ + "name": "open-search", + "displayName": "OpenSearch", + "version": "1.0.3", + "author": { + "name": "SquaredUp Labs", + "type": "labs" + }, + "description": "Query OpenSearch databases using DSL.", + "category": "Database", + "type": "cloud", + "restrictedToPlatforms": [], + "importNotSupported": true, + "schemaVersion": "2.0", + "base": { + "plugin": "WebAPI", + "majorVersion": "1", + "config": { + "authMode": "{{authMode}}", + "basicAuthUsername": "{{basicAuthUsername}}", + "basicAuthPassword": "{{basicAuthPassword}}", + "queryArgs": [], + "headers": [ + { + "key": "Content-Type", + "value": "application/json" + } + ], + "baseUrl": "{{instanceUrl}}", + "ignoreCertificateErrors": "{{ignoreCertificateErrors}}" + } + } +} \ No newline at end of file diff --git a/plugins/OpenSearch/v1/ui.json b/plugins/OpenSearch/v1/ui.json new file mode 100644 index 0000000..146cdfd --- /dev/null +++ b/plugins/OpenSearch/v1/ui.json @@ -0,0 +1,60 @@ +[ + { + "type": "text", + "name": "instanceUrl", + "label": "Instance URL", + "validation": { "required": true }, + "placeholder": "Instance URL" + }, + { + "name": "authMode", + "type": "radio", + "label": "Authentication", + "help": "**Basic:** Authenticate with username and password. \n**Anonymous access:** No authentication required", + "defaultValue": "apiKeyAuth", + "validation": { + "required": true + }, + "options": [ + { + "label": "Basic", + "value": "basic" + }, + { + "label": "Anonymous access", + "value": "none" + } + + ] + }, + { + "type": "fieldGroup", + "visible": { + "authType": "basicAuth" + }, + "fields": [ + { + "type": "text", + "name": "basicAuthUsername", + "label": "Username", + "title": "Username", + "validation": { "required": true }, + "placeholder": "Enter a username" + }, + { + "type": "password", + "name": "basicAuthPassword", + "label": "Password", + "title": "Password", + "validation": { "required": true }, + "placeholder": "Enter a password" + } + ] + }, + { + "type": "checkbox", + "name": "ignoreCertificateErrors", + "label": "Ignore certificate errors", + "help": "Ignore certificate errors when connecting to an OpenSearch instance with a self-signed certificate" + } +] From 1fe09dc8e5c431d5a99cf13f5ccce0752980ce3d Mon Sep 17 00:00:00 2001 From: richbenwell Date: Sun, 8 Feb 2026 22:20:34 -0500 Subject: [PATCH 2/8] Fix fieldGroup visibility --- plugins/OpenSearch/v1/ui.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/plugins/OpenSearch/v1/ui.json b/plugins/OpenSearch/v1/ui.json index 146cdfd..abf257a 100644 --- a/plugins/OpenSearch/v1/ui.json +++ b/plugins/OpenSearch/v1/ui.json @@ -30,7 +30,7 @@ { "type": "fieldGroup", "visible": { - "authType": "basicAuth" + "authMode": "basic" }, "fields": [ { From c60b132851be94b662e6a27b8a5bdcc826625244 Mon Sep 17 00:00:00 2001 From: richbenwell Date: Tue, 10 Feb 2026 14:43:26 -0500 Subject: [PATCH 3/8] Fix authMode default --- plugins/OpenSearch/v1/ui.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/plugins/OpenSearch/v1/ui.json b/plugins/OpenSearch/v1/ui.json index abf257a..b3ddc1b 100644 --- a/plugins/OpenSearch/v1/ui.json +++ b/plugins/OpenSearch/v1/ui.json @@ -11,7 +11,7 @@ "type": "radio", "label": "Authentication", "help": "**Basic:** Authenticate with username and password. \n**Anonymous access:** No authentication required", - "defaultValue": "apiKeyAuth", + "defaultValue": "basic", "validation": { "required": true }, From 9fb791140896fd30811597868e983e9e41123abd Mon Sep 17 00:00:00 2001 From: richbenwell Date: Tue, 10 Feb 2026 14:58:26 -0500 Subject: [PATCH 4/8] Use visibility field instead of noMatch and add docs --- plugins/OpenSearch/v1/README.md | 2 +- .../OpenSearch/v1/dataStreams/indices.json | 4 ++-- plugins/OpenSearch/v1/docs/setup.md | 19 +++++++++++++++++++ 3 files changed, 22 insertions(+), 3 deletions(-) diff --git a/plugins/OpenSearch/v1/README.md b/plugins/OpenSearch/v1/README.md index 374021e..2a590c5 100644 --- a/plugins/OpenSearch/v1/README.md +++ b/plugins/OpenSearch/v1/README.md @@ -1,6 +1,6 @@ ## Overview -Query OpenSearch databases. This plugin is primarily a wrapper around the `_search` API endpoint that allows for a range of queries. +Query OpenSearch databases using DSL. This plugin is primarily a wrapper around the `_search` API endpoint that allows for a range of queries. See the [OpenSearch API docs](https://docs.opensearch.org/latest/api-reference/search-apis/search/) for more information. diff --git a/plugins/OpenSearch/v1/dataStreams/indices.json b/plugins/OpenSearch/v1/dataStreams/indices.json index b41f905..bc2a253 100644 --- a/plugins/OpenSearch/v1/dataStreams/indices.json +++ b/plugins/OpenSearch/v1/dataStreams/indices.json @@ -14,8 +14,8 @@ }, "timeframes": false, "matches": "none", - "options": { - "noMatch": true + "visibility": { + "type": "hidden" }, "metadata": [ { diff --git a/plugins/OpenSearch/v1/docs/setup.md b/plugins/OpenSearch/v1/docs/setup.md index e69de29..ee9632b 100644 --- a/plugins/OpenSearch/v1/docs/setup.md +++ b/plugins/OpenSearch/v1/docs/setup.md @@ -0,0 +1,19 @@ +## Instance URL + +The base URL of your OpenSearch database. + +For example: +`https://:9200` + +Do *not* include the `/api' path. + +## Authentication + +The data source supports basic (username and password) or anonymous authentication. + +If using basic authentication, ensure the user only has read permissions. + +If using anonymous, ensure the endpoint is secured in some other form. + +If you need to whitelist the IP addresses for SquaredUp these can be found on the [Data Security](https://docs.squaredup.com/reference/security/data-security) KB article. + From b9cd25c41e4e4cbf77293b9f975607d31e7561b2 Mon Sep 17 00:00:00 2001 From: richbenwell Date: Wed, 11 Feb 2026 16:26:14 -0500 Subject: [PATCH 5/8] Address Copilot PR review comments --- .../OpenSearch/v1/dataStreams/scripts/search.js | 2 +- plugins/OpenSearch/v1/docs/setup.md | 4 +++- plugins/OpenSearch/v1/metadata.json | 14 +++++++++++++- plugins/OpenSearch/v1/ui.json | 4 +--- 4 files changed, 18 insertions(+), 6 deletions(-) diff --git a/plugins/OpenSearch/v1/dataStreams/scripts/search.js b/plugins/OpenSearch/v1/dataStreams/scripts/search.js index ea8bc45..ccbf2b2 100644 --- a/plugins/OpenSearch/v1/dataStreams/scripts/search.js +++ b/plugins/OpenSearch/v1/dataStreams/scripts/search.js @@ -1,4 +1,4 @@ -if (data.aggregations) { +if (data.aggregations && data.aggregations.length > 0) { const agg = data.aggregations[Object.keys(data.aggregations).at(-1)]; // last aggregation to support pipelining diff --git a/plugins/OpenSearch/v1/docs/setup.md b/plugins/OpenSearch/v1/docs/setup.md index ee9632b..73ba1f4 100644 --- a/plugins/OpenSearch/v1/docs/setup.md +++ b/plugins/OpenSearch/v1/docs/setup.md @@ -1,3 +1,5 @@ +# Configuration + ## Instance URL The base URL of your OpenSearch database. @@ -5,7 +7,7 @@ The base URL of your OpenSearch database. For example: `https://:9200` -Do *not* include the `/api' path. +Do *not* include the `/api` path. ## Authentication diff --git a/plugins/OpenSearch/v1/metadata.json b/plugins/OpenSearch/v1/metadata.json index 1f9cfe7..5a0f709 100644 --- a/plugins/OpenSearch/v1/metadata.json +++ b/plugins/OpenSearch/v1/metadata.json @@ -29,5 +29,17 @@ "baseUrl": "{{instanceUrl}}", "ignoreCertificateErrors": "{{ignoreCertificateErrors}}" } - } + }, + "links": [ + { + "category": "documentation", + "url": "https://github.com/squaredup/plugins/blob/main/plugins/OpenSearch/v1/docs/setup.md", + "label": "Help adding this plugin" + }, + { + "category": "source", + "url": "https://github.com/squaredup/plugins/tree/main/plugins/OpenSearch/v1", + "label": "Repository" + } + ], } \ No newline at end of file diff --git a/plugins/OpenSearch/v1/ui.json b/plugins/OpenSearch/v1/ui.json index b3ddc1b..8ec9c70 100644 --- a/plugins/OpenSearch/v1/ui.json +++ b/plugins/OpenSearch/v1/ui.json @@ -4,7 +4,7 @@ "name": "instanceUrl", "label": "Instance URL", "validation": { "required": true }, - "placeholder": "Instance URL" + "placeholder": "Enter the OpenSearch URL" }, { "name": "authMode", @@ -37,7 +37,6 @@ "type": "text", "name": "basicAuthUsername", "label": "Username", - "title": "Username", "validation": { "required": true }, "placeholder": "Enter a username" }, @@ -45,7 +44,6 @@ "type": "password", "name": "basicAuthPassword", "label": "Password", - "title": "Password", "validation": { "required": true }, "placeholder": "Enter a password" } From e080067567d7dc7a046e4ff87c487734f2ac119a Mon Sep 17 00:00:00 2001 From: richbenwell Date: Wed, 11 Feb 2026 20:35:41 -0500 Subject: [PATCH 6/8] Remove trailing comma --- plugins/OpenSearch/v1/metadata.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/plugins/OpenSearch/v1/metadata.json b/plugins/OpenSearch/v1/metadata.json index 5a0f709..95342bc 100644 --- a/plugins/OpenSearch/v1/metadata.json +++ b/plugins/OpenSearch/v1/metadata.json @@ -41,5 +41,5 @@ "url": "https://github.com/squaredup/plugins/tree/main/plugins/OpenSearch/v1", "label": "Repository" } - ], + ] } \ No newline at end of file From 2efb9c28da718f4b46ceefd9605a0c12bd8b5c9e Mon Sep 17 00:00:00 2001 From: richbenwell Date: Fri, 13 Feb 2026 13:28:17 -0500 Subject: [PATCH 7/8] Fix length check --- plugins/OpenSearch/v1/dataStreams/scripts/search.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/plugins/OpenSearch/v1/dataStreams/scripts/search.js b/plugins/OpenSearch/v1/dataStreams/scripts/search.js index ccbf2b2..ac1d505 100644 --- a/plugins/OpenSearch/v1/dataStreams/scripts/search.js +++ b/plugins/OpenSearch/v1/dataStreams/scripts/search.js @@ -1,4 +1,4 @@ -if (data.aggregations && data.aggregations.length > 0) { +if (data.aggregations && Object.keys(data.aggregations).length > 0) { const agg = data.aggregations[Object.keys(data.aggregations).at(-1)]; // last aggregation to support pipelining From 303e981980add8ec41142d95c33ae2ec8609c9d9 Mon Sep 17 00:00:00 2001 From: richbenwell Date: Fri, 13 Feb 2026 13:30:03 -0500 Subject: [PATCH 8/8] Remove whitespace --- plugins/OpenSearch/v1/dataStreams/scripts/search.js | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/plugins/OpenSearch/v1/dataStreams/scripts/search.js b/plugins/OpenSearch/v1/dataStreams/scripts/search.js index ac1d505..cc8c056 100644 --- a/plugins/OpenSearch/v1/dataStreams/scripts/search.js +++ b/plugins/OpenSearch/v1/dataStreams/scripts/search.js @@ -26,7 +26,4 @@ if (data.aggregations && Object.keys(data.aggregations).length > 0) { result = data.hits.hits.map(hit => hit._source); -} - - - +} \ No newline at end of file