From c9f6eacf33c38eb18f4b3a6605f58732dcf1d10c Mon Sep 17 00:00:00 2001 From: Sarat Vemulapalli Date: Sun, 24 Jul 2022 22:55:48 -0700 Subject: [PATCH 1/6] Initial draft of Design for extensions Signed-off-by: Sarat Vemulapalli --- DESIGN.md | 71 ++++++++++++++++++++++++++++++++++++++++++++ Docs/Extensions.png | Bin 0 -> 43920 bytes Docs/plugins.png | Bin 0 -> 34443 bytes 3 files changed, 71 insertions(+) create mode 100644 DESIGN.md create mode 100644 Docs/Extensions.png create mode 100644 Docs/plugins.png diff --git a/DESIGN.md b/DESIGN.md new file mode 100644 index 00000000..898c98d8 --- /dev/null +++ b/DESIGN.md @@ -0,0 +1,71 @@ +# Extensions + +*Note*: This document is evolving and is in draft state. + +Plugin architecture enables extending core features of OpenSearch. There are various kinds of plugins which are supported. +But, the architecture has significant problems for OpenSearch customers. Importantly, plugins can fatally impact the cluster +i.e critical workloads like ingestion/search traffic would be impacted because of a non-critical plugin like s3-repository failed with an exception. + +This problem is exponentially grows when we would like to run a 3rd Party plugin from the community. +As OpenSearch and plugins run in the same process, it brings in security risk, dependency conflicts and reduces the velocity of releases. + +Introducing extensions, a simple and easy way to extend features of OpenSearch. It would support all plugin features and enable them to run in a different process or another node via OpenSearch SDK. + +Meta Issue: [Steps to make OpenSearch extensible](https://github.com/opensearch-project/OpenSearch/issues/2447) +Sandboxing: [Step towards modular architecture in OpenSearch](https://github.com/opensearch-project/OpenSearch/issues/1422) +Security: [Security for extensions](SECURITY.md) + +## Plugins Architecture + +![](Docs/plugins.png) + +Plugins are installed via [`opensearch-plugin`](https://github.com/opensearch-project/OpenSearch/blob/main/distribution/tools/plugin-cli/src/main/java/org/opensearch/plugins/InstallPluginCommand.java) and are class loaded into OpenSearch. +Plugins run within OpenSearch as a single process. Plugins interface with OpenSearch via extension points which plug into the core modules of OpenSearch. +This [blog post](https://opensearch.org/blog/technical-post/2021/12/plugins-intro/) helps untangle how plugins work. + +Walking through an example, a Plugin would like to register a custom setting which could be toggled via Rest API by the user. +The plugin uses compiles with OpenSearch x.y.z version and generates a `.zip`. +This `.zip` file is installed via `opensearch-plugin` tool which unpacks the code and places it under `~/plugins/`. +During the bootstrap of OpenSearch node, it class loads all the code under `~/plugins/` directory. `Node.java` makes a call to get all settings the plugins would like to register. These settings are used as `additionalSettings` and construct `SettingsModule` instance which tracks all settings. + +## Extensions Architecture + +![](Docs/Extensions.png) + +Extensions are independent processes which are built using `opensearch-sdk`. They communicate with OpenSearch via [transport](https://github.com/opensearch-project/OpenSearch/tree/main/modules/transport-netty4) protocol which today is used to communicate between OpenSearch nodes. +Extensions are designed to extend features via APIs which are exposed using extension points of OpenSearch. + +### Discovery +Extensions are discovered and configured via `extensions.yml` which is read by OpenSearch during the node bootstrap. `ExtensionsOrchestrator` reads through the config file at `~/extensions` and registers extensions within OpenSearch. +Here is an example extension configuration `extensions.yml`: + +``` +extensions: + - name: opensearch-sdk + uniqueId: opensearch-sdk-1 + hostName: 'sdk_host' + hostAddress: '127.0.0.1' + port: '4532' + version: '1.0' + description: Extension for the Opensearch SDK Repo + opensearchVersion: '3.0.0' + javaVersion: '14' + className: ExtensionsRunner + customFolderName: opensearch-sdk + hasNativeController: false +``` + + +### Communication + +### OpenSearch SDK + +### Settings +Walking through a similar example as plugin above, after extension registration is done, extension makes an API call to register custom settings to OpenSearch. +`ExtensionsOrchestrator` recieves the requests, forwards it to `SettingsModule` to register a new setting and wala, the user is now able to toggle the setting via `_settings` Rest API. + +## FAQ + +- Will extensions replace plugins? + We see value in plugins as they are high performant which works well for index/search workloads. + \ No newline at end of file diff --git a/Docs/Extensions.png b/Docs/Extensions.png new file mode 100644 index 0000000000000000000000000000000000000000..dff629fb496a29230a4ddbeed99d0f56dfe974a4 GIT binary patch literal 43920 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 literal 0 HcmV?d00001 diff --git a/Docs/plugins.png b/Docs/plugins.png new file mode 100644 index 0000000000000000000000000000000000000000..a1eb65172211e107ceb4b9df6d31d7b82c8fc08a GIT binary patch literal 34443 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 literal 0 HcmV?d00001 From cccd4bcfbf208ad5039ae6487e1899928f6088d6 Mon Sep 17 00:00:00 2001 From: Sarat Vemulapalli Date: Mon, 25 Jul 2022 10:07:47 -0700 Subject: [PATCH 2/6] Adding TBD sections Signed-off-by: Sarat Vemulapalli --- DESIGN.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/DESIGN.md b/DESIGN.md index 898c98d8..c7a7e716 100644 --- a/DESIGN.md +++ b/DESIGN.md @@ -57,8 +57,10 @@ extensions: ### Communication +TBD ### OpenSearch SDK +TBD ### Settings Walking through a similar example as plugin above, after extension registration is done, extension makes an API call to register custom settings to OpenSearch. From f23c93dc1c8280d87449214c996c11ec7360406b Mon Sep 17 00:00:00 2001 From: Owais Kazi Date: Mon, 25 Jul 2022 14:22:41 -0700 Subject: [PATCH 3/6] Added communcation, sdk and latency Signed-off-by: Owais Kazi --- DESIGN.md | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/DESIGN.md b/DESIGN.md index c7a7e716..0ec8f651 100644 --- a/DESIGN.md +++ b/DESIGN.md @@ -57,10 +57,13 @@ extensions: ### Communication -TBD +As we are running extensions on the port defined in the `extensions.yml`, the communication between OpenSearch and Extensions happens using a ServerSocket which binds the port and the host address. OpenSearch will initialize the extensions during the bootstrap by making a request to all the extensions running on different ports and thus creating a medium for the future requests. ### OpenSearch SDK -TBD +Currently, plugins relies on extension points to communicate with OpenSearch. To turn plugins into extensions, all the extension points should be converted into Transport APIs which will be present in the SDK. Plugins need to integrate SDK, call those APIs, and later SDK will take care of the communication and the required attributes from OpenSearch. + +### Latency +https://github.com/opensearch-project/OpenSearch/issues/3012#issuecomment-1122682444 ### Settings Walking through a similar example as plugin above, after extension registration is done, extension makes an API call to register custom settings to OpenSearch. From a2cdb7dbae7b2476fc8395a15581dd4281c71bcf Mon Sep 17 00:00:00 2001 From: Owais Kazi Date: Mon, 25 Jul 2022 14:26:05 -0700 Subject: [PATCH 4/6] Lint errors Signed-off-by: Owais Kazi --- DESIGN.md | 1 - 1 file changed, 1 deletion(-) diff --git a/DESIGN.md b/DESIGN.md index 0ec8f651..f997fa3c 100644 --- a/DESIGN.md +++ b/DESIGN.md @@ -73,4 +73,3 @@ Walking through a similar example as plugin above, after extension registration - Will extensions replace plugins? We see value in plugins as they are high performant which works well for index/search workloads. - \ No newline at end of file From 2cc77ab1c1f0b786aad38b23a2246e22d4ca0321 Mon Sep 17 00:00:00 2001 From: Owais Kazi Date: Mon, 25 Jul 2022 17:24:23 -0700 Subject: [PATCH 5/6] Moved Latency to FAQ Signed-off-by: Owais Kazi --- DESIGN.md | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/DESIGN.md b/DESIGN.md index f997fa3c..a976cddf 100644 --- a/DESIGN.md +++ b/DESIGN.md @@ -62,9 +62,6 @@ As we are running extensions on the port defined in the `extensions.yml`, the co ### OpenSearch SDK Currently, plugins relies on extension points to communicate with OpenSearch. To turn plugins into extensions, all the extension points should be converted into Transport APIs which will be present in the SDK. Plugins need to integrate SDK, call those APIs, and later SDK will take care of the communication and the required attributes from OpenSearch. -### Latency -https://github.com/opensearch-project/OpenSearch/issues/3012#issuecomment-1122682444 - ### Settings Walking through a similar example as plugin above, after extension registration is done, extension makes an API call to register custom settings to OpenSearch. `ExtensionsOrchestrator` recieves the requests, forwards it to `SettingsModule` to register a new setting and wala, the user is now able to toggle the setting via `_settings` Rest API. @@ -73,3 +70,5 @@ Walking through a similar example as plugin above, after extension registration - Will extensions replace plugins? We see value in plugins as they are high performant which works well for index/search workloads. +- How is the latency going to be for extensions? + https://github.com/opensearch-project/OpenSearch/issues/3012#issuecomment-1122682444 From 2b17fe1fbaa7d32fe190f3c1e993c7c86906c4ff Mon Sep 17 00:00:00 2001 From: Sarat Vemulapalli Date: Tue, 26 Jul 2022 10:31:29 -0700 Subject: [PATCH 6/6] Readdressing comments Signed-off-by: Sarat Vemulapalli --- DESIGN.md | 30 +++++++++++++----------------- 1 file changed, 13 insertions(+), 17 deletions(-) diff --git a/DESIGN.md b/DESIGN.md index a976cddf..6f598f81 100644 --- a/DESIGN.md +++ b/DESIGN.md @@ -9,7 +9,7 @@ i.e critical workloads like ingestion/search traffic would be impacted because o This problem is exponentially grows when we would like to run a 3rd Party plugin from the community. As OpenSearch and plugins run in the same process, it brings in security risk, dependency conflicts and reduces the velocity of releases. -Introducing extensions, a simple and easy way to extend features of OpenSearch. It would support all plugin features and enable them to run in a different process or another node via OpenSearch SDK. +Introducing extensions, a simple and easy way to extend features of OpenSearch. It would support all plugin features and enable them to run in a seperate process or on another node via OpenSearch SDK. Meta Issue: [Steps to make OpenSearch extensible](https://github.com/opensearch-project/OpenSearch/issues/2447) Sandboxing: [Step towards modular architecture in OpenSearch](https://github.com/opensearch-project/OpenSearch/issues/1422) @@ -33,26 +33,22 @@ During the bootstrap of OpenSearch node, it class loads all the code under `~/pl ![](Docs/Extensions.png) Extensions are independent processes which are built using `opensearch-sdk`. They communicate with OpenSearch via [transport](https://github.com/opensearch-project/OpenSearch/tree/main/modules/transport-netty4) protocol which today is used to communicate between OpenSearch nodes. -Extensions are designed to extend features via APIs which are exposed using extension points of OpenSearch. +Extensions are designed to extend features via transport APIs which are exposed using extension points of OpenSearch. ### Discovery -Extensions are discovered and configured via `extensions.yml` which is read by OpenSearch during the node bootstrap. `ExtensionsOrchestrator` reads through the config file at `~/extensions` and registers extensions within OpenSearch. +Extensions are discovered and configured via `extensions.yml`, same way we currently have `plugin-descriptor.properties` which is read by OpenSearch during the node bootstrap. `ExtensionsOrchestrator` reads through the config file at `~/extensions` and registers extensions within OpenSearch. Here is an example extension configuration `extensions.yml`: ``` extensions: - - name: opensearch-sdk - uniqueId: opensearch-sdk-1 - hostName: 'sdk_host' - hostAddress: '127.0.0.1' - port: '4532' - version: '1.0' - description: Extension for the Opensearch SDK Repo - opensearchVersion: '3.0.0' - javaVersion: '14' - className: ExtensionsRunner - customFolderName: opensearch-sdk - hasNativeController: false + - name: opensearch-sdk // extension name + uniqueId: opensearch-sdk-1 // identifier for the extension + hostName: 'sdk_host' // name of the host where extension is running + hostAddress: '127.0.0.1' // host to reach + port: '4532' // port to reach + version: '1.0' // extension version + description: Extension for the Opensearch SDK Repo // description of the extension + opensearchVersion: '3.0.0' // OpenSearch compatibility ``` @@ -64,11 +60,11 @@ Currently, plugins relies on extension points to communicate with OpenSearch. To ### Settings Walking through a similar example as plugin above, after extension registration is done, extension makes an API call to register custom settings to OpenSearch. -`ExtensionsOrchestrator` recieves the requests, forwards it to `SettingsModule` to register a new setting and wala, the user is now able to toggle the setting via `_settings` Rest API. +`ExtensionsOrchestrator` receives the requests, forwards it to `SettingsModule` to register a new setting and wala, the user is now able to toggle the setting via `_settings` Rest API. ## FAQ - Will extensions replace plugins? - We see value in plugins as they are high performant which works well for index/search workloads. + Plugins will continue to be supported and extensions are preferred as they will be easier to develop, deploy, and operate. - How is the latency going to be for extensions? https://github.com/opensearch-project/OpenSearch/issues/3012#issuecomment-1122682444