You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@dolphinscheduler.apache.org by we...@apache.org on 2022/07/26 06:51:55 UTC
[dolphinscheduler] branch dev updated: Add base loop task execotor and http template parser (#11137)
This is an automated email from the ASF dual-hosted git repository.
wenjun pushed a commit to branch dev
in repository https://gitbox.apache.org/repos/asf/dolphinscheduler.git
The following commit(s) were added to refs/heads/dev by this push:
new c7789bf049 Add base loop task execotor and http template parser (#11137)
c7789bf049 is described below
commit c7789bf0499f5893810d93e144250544a528caa4
Author: Wenjun Ruan <we...@apache.org>
AuthorDate: Tue Jul 26 14:51:50 2022 +0800
Add base loop task execotor and http template parser (#11137)
* Add base loop task execotor and http template parser
* Add JsonPathUtils
---
.gitignore | 1 +
dolphinscheduler-bom/pom.xml | 14 ++
dolphinscheduler-dist/release-docs/LICENSE | 4 +
.../licenses/LICENSE-accessors-smart.txt | 201 ++++++++++++++++++++
.../release-docs/licenses/LICENSE-asm.txt | 27 +++
.../release-docs/licenses/LICENSE-json-path.txt | 202 +++++++++++++++++++++
.../release-docs/licenses/LICENSE-json-smart.txt | 201 ++++++++++++++++++++
.../dolphinscheduler-task-api/pom.xml | 8 +
.../plugin/task/api/AbstractTask.java | 2 +-
.../plugin/task/api/TaskConstants.java | 4 +
.../plugin/task/api/loop/BaseLoopTaskExecutor.java | 106 +++++++++++
.../api/loop/LoopTaskCancelMethodDefinition.java | 26 +++
.../plugin/task/api/loop/LoopTaskDefinition.java | 48 +++++
.../plugin/task/api/loop/LoopTaskInstanceInfo.java | 30 +++
.../task/api/loop/LoopTaskInstanceStatus.java | 29 +++
.../task/api/loop/LoopTaskMethodDefinition.java | 26 +++
.../plugin/task/api/loop/LoopTaskMethodType.java | 23 +++
.../loop/LoopTaskQueryStatusMethodDefinition.java | 34 ++++
.../loop/LoopTaskSubmitTaskMethodDefinition.java | 26 +++
.../api/loop/template/LoopTaskYamlDefinition.java | 82 +++++++++
.../api/loop/template/TaskDefinitionParser.java | 32 ++++
.../loop/template/TemplateMethodTransformer.java | 32 ++++
.../http/BaseHttpTemplateLoopTaskExecutor.java | 57 ++++++
.../loop/template/http/HttpLoopTaskDefinition.java | 64 +++++++
.../template/http/HttpLoopTaskInstanceInfo.java | 31 ++++
.../template/http/HttpLoopTaskInstanceStatus.java | 31 ++++
.../http/HttpLoopTaskMethodDefinition.java | 43 +++++
.../HttpLoopTaskCancelTaskMethodDefinition.java | 80 ++++++++
.../HttpLoopTaskQueryStatusMethodDefinition.java | 87 +++++++++
.../HttpLoopTaskSubmitTaskMethodDefinition.java | 75 ++++++++
.../parser/CancelTemplateMethodTransformer.java | 46 +++++
.../http/parser/HttpTaskDefinitionParser.java | 77 ++++++++
.../QueryStateTemplateMethodTransformer.java | 48 +++++
.../parser/SubmitTemplateMethodTransformer.java | 48 +++++
.../plugin/task/api/utils/JsonPathUtils.java | 54 ++++++
.../plugin/task/api/utils/OkHttpUtils.java | 99 ++++++++++
.../plugin/task/api/utils/RetryUtils.java | 75 ++++++++
.../http/parser/HttpTaskDefinitionParserTest.java | 51 ++++++
.../plugin/task/api/utils/JsonPathUtilsTest.java | 40 ++++
.../plugin/task/api/utils/RetryUtilsTest.java | 39 ++++
.../src/test/resources/mock_loop_task.yaml | 36 ++++
tools/dependencies/known-dependencies.txt | 4 +
42 files changed, 2242 insertions(+), 1 deletion(-)
diff --git a/.gitignore b/.gitignore
index fbc74e41d1..a553ba02af 100644
--- a/.gitignore
+++ b/.gitignore
@@ -49,6 +49,7 @@ dolphinscheduler-ui/node
dolphinscheduler-common/sql
dolphinscheduler-common/test
dolphinscheduler-worker/logs
+dolphinscheduler-master/logs
dolphinscheduler-api/logs
# ------------------
diff --git a/dolphinscheduler-bom/pom.xml b/dolphinscheduler-bom/pom.xml
index 588c79b34d..e142747ee7 100644
--- a/dolphinscheduler-bom/pom.xml
+++ b/dolphinscheduler-bom/pom.xml
@@ -87,6 +87,8 @@
<hibernate-validator.version>6.2.2.Final</hibernate-validator.version>
<aws-sdk.version>1.12.160</aws-sdk.version>
<joda-time.version>2.10.13</joda-time.version>
+ <okhttp.version>3.14.9</okhttp.version>
+ <json-path.version>2.7.0</json-path.version>
</properties>
@@ -603,6 +605,18 @@
<version>${aws-sdk.version}</version>
</dependency>
+ <dependency>
+ <groupId>com.squareup.okhttp3</groupId>
+ <artifactId>okhttp</artifactId>
+ <version>${okhttp.version}</version>
+ </dependency>
+
+ <dependency>
+ <groupId>com.jayway.jsonpath</groupId>
+ <artifactId>json-path</artifactId>
+ <version>${json-path.version}</version>
+ </dependency>
+
</dependencies>
</dependencyManagement>
diff --git a/dolphinscheduler-dist/release-docs/LICENSE b/dolphinscheduler-dist/release-docs/LICENSE
index adb79ca250..5cda9c8076 100644
--- a/dolphinscheduler-dist/release-docs/LICENSE
+++ b/dolphinscheduler-dist/release-docs/LICENSE
@@ -215,6 +215,7 @@ Apache 2.0 licenses
The following components are provided under the Apache License. See project link for details.
The text of each license is also included at licenses/LICENSE-[project].txt.
+ accessors-smart 2.4.7: https://github.com/netplex/json-smart-v2, Apache 2.0
apacheds-i18n 2.0.0-M15: https://mvnrepository.com/artifact/org.apache.directory.server/apacheds-i18n/2.0.0-M15, Apache 2.0
apacheds-kerberos-codec 2.0.0-M15: https://mvnrepository.com/artifact/org.apache.directory.server/apacheds-kerberos-codec/2.0.0-M15, Apache 2.0
tomcat-embed-el 9.0.54: https://mvnrepository.com/artifact/org.apache.tomcat.embed/tomcat-embed-el/9.0.54, Apache 2.0
@@ -313,6 +314,8 @@ The text of each license is also included at licenses/LICENSE-[project].txt.
jna-platform 5.10.0: https://mvnrepository.com/artifact/net.java.dev.jna/jna-platform/5.10.0, Apache 2.0 and LGPL 2.1
joda-time 2.10.13: https://github.com/JodaOrg/joda-time, Apache 2.0
jpam 1.1: https://mvnrepository.com/artifact/net.sf.jpam/jpam/1.1, Apache 2.0
+ json-path 2.7.0: https://github.com/json-path/JsonPath, Apache 2.0
+ json-smart 2.4.7: https://github.com/netplex/json-smart-v2, Apache 2.0
jsqlparser 2.1: https://github.com/JSQLParser/JSqlParser, Apache 2.0 or LGPL 2.1
jsr305 3.0.0: https://mvnrepository.com/artifact/com.google.code.findbugs/jsr305, Apache 2.0
j2objc-annotations 1.1 https://mvnrepository.com/artifact/com.google.j2objc/j2objc-annotations/1.1, Apache 2.0
@@ -450,6 +453,7 @@ BSD licenses
The following components are provided under a BSD license. See project link for details.
The text of each license is also included at licenses/LICENSE-[project].txt.
+ asm 9.1: https://gitlab.ow2.org/asm/asm, BSD 3-Clause
click 8.0: https://github.com/pallets/click, BSD 3-Clause
curvesapi 1.06: https://mvnrepository.com/artifact/com.github.virtuald/curvesapi/1.06, BSD 3-clause
javolution 5.5.1: https://mvnrepository.com/artifact/javolution/javolution/5.5.1, BSD
diff --git a/dolphinscheduler-dist/release-docs/licenses/LICENSE-accessors-smart.txt b/dolphinscheduler-dist/release-docs/licenses/LICENSE-accessors-smart.txt
new file mode 100644
index 0000000000..9c8f3ea087
--- /dev/null
+++ b/dolphinscheduler-dist/release-docs/licenses/LICENSE-accessors-smart.txt
@@ -0,0 +1,201 @@
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "{}"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright {yyyy} {name of copyright owner}
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
\ No newline at end of file
diff --git a/dolphinscheduler-dist/release-docs/licenses/LICENSE-asm.txt b/dolphinscheduler-dist/release-docs/licenses/LICENSE-asm.txt
new file mode 100644
index 0000000000..631ee53c53
--- /dev/null
+++ b/dolphinscheduler-dist/release-docs/licenses/LICENSE-asm.txt
@@ -0,0 +1,27 @@
+ASM: a very small and fast Java bytecode manipulation framework
+Copyright (c) 2000-2011 INRIA, France Telecom
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions
+are met:
+1. Redistributions of source code must retain the above copyright
+ notice, this list of conditions and the following disclaimer.
+2. Redistributions in binary form must reproduce the above copyright
+ notice, this list of conditions and the following disclaimer in the
+ documentation and/or other materials provided with the distribution.
+3. Neither the name of the copyright holders nor the names of its
+ contributors may be used to endorse or promote products derived from
+ this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+THE POSSIBILITY OF SUCH DAMAGE.
\ No newline at end of file
diff --git a/dolphinscheduler-dist/release-docs/licenses/LICENSE-json-path.txt b/dolphinscheduler-dist/release-docs/licenses/LICENSE-json-path.txt
new file mode 100644
index 0000000000..70eda5041a
--- /dev/null
+++ b/dolphinscheduler-dist/release-docs/licenses/LICENSE-json-path.txt
@@ -0,0 +1,202 @@
+
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright 2017 Jayway
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
\ No newline at end of file
diff --git a/dolphinscheduler-dist/release-docs/licenses/LICENSE-json-smart.txt b/dolphinscheduler-dist/release-docs/licenses/LICENSE-json-smart.txt
new file mode 100644
index 0000000000..9c8f3ea087
--- /dev/null
+++ b/dolphinscheduler-dist/release-docs/licenses/LICENSE-json-smart.txt
@@ -0,0 +1,201 @@
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "{}"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright {yyyy} {name of copyright owner}
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
\ No newline at end of file
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/pom.xml b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/pom.xml
index 0039f879ad..a53870d255 100644
--- a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/pom.xml
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/pom.xml
@@ -36,6 +36,14 @@
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-annotation</artifactId>
</dependency>
+ <dependency>
+ <groupId>com.squareup.okhttp3</groupId>
+ <artifactId>okhttp</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>com.jayway.jsonpath</groupId>
+ <artifactId>json-path</artifactId>
+ </dependency>
<dependency>
<groupId>commons-io</groupId>
<artifactId>commons-io</artifactId>
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/AbstractTask.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/AbstractTask.java
index 9bf560266c..060609858e 100644
--- a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/AbstractTask.java
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/AbstractTask.java
@@ -34,7 +34,7 @@ public abstract class AbstractTask {
/**
* taskExecutionContext
**/
- TaskExecutionContext taskRequest;
+ protected TaskExecutionContext taskRequest;
/**
* SHELL process pid
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/TaskConstants.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/TaskConstants.java
index 03010825fa..56d2ca467f 100644
--- a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/TaskConstants.java
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/TaskConstants.java
@@ -17,6 +17,7 @@
package org.apache.dolphinscheduler.plugin.task.api;
+import java.time.Duration;
import java.util.Arrays;
import java.util.List;
@@ -427,4 +428,7 @@ public class TaskConstants {
*/
public static final String CONDA_PATH = "conda.path";
+ // Loop task constants
+ public static final Duration DEFAULT_LOOP_STATUS_INTERVAL = Duration.ofSeconds(5L);
+
}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/BaseLoopTaskExecutor.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/BaseLoopTaskExecutor.java
new file mode 100644
index 0000000000..15dd25e236
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/BaseLoopTaskExecutor.java
@@ -0,0 +1,106 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop;
+
+import org.apache.dolphinscheduler.plugin.task.api.AbstractTaskExecutor;
+import org.apache.dolphinscheduler.plugin.task.api.TaskConstants;
+import org.apache.dolphinscheduler.plugin.task.api.TaskException;
+import org.apache.dolphinscheduler.plugin.task.api.TaskExecutionContext;
+import org.apache.dolphinscheduler.plugin.task.api.utils.RetryUtils;
+
+import java.time.Duration;
+
+import javax.annotation.Nullable;
+
+import lombok.NonNull;
+
+/**
+ * This class is the base class for all loop task type.
+ * <p>
+ * The loop task type means, we will submit a task, and loop the task status until the task is finished.
+ */
+public abstract class BaseLoopTaskExecutor extends AbstractTaskExecutor {
+
+ /**
+ * The task instance info will be set when task has submitted successful.
+ */
+ protected @Nullable LoopTaskInstanceInfo loopTaskInstanceInfo;
+
+ protected BaseLoopTaskExecutor(@NonNull TaskExecutionContext taskExecutionContext) {
+ super(taskExecutionContext);
+ }
+
+ @Override
+ public void handle() throws TaskException {
+ try {
+ final long loopInterval = getTaskInstanceStatusQueryInterval().toMillis();
+ loopTaskInstanceInfo = submitLoopTask();
+ this.appIds = loopTaskInstanceInfo.getTaskInstanceId();
+ // loop the task status until the task is finished or task has been canceled.
+ // we use retry utils here to avoid the task status query failure due to network failure.
+ // the default retry policy is 3 times, and the interval is 1 second.
+ while (!cancel
+ && !RetryUtils.retryFunction(() -> queryTaskInstanceStatus(loopTaskInstanceInfo).isFinished())) {
+ Thread.sleep(loopInterval);
+ }
+ } catch (InterruptedException e) {
+ setExitStatusCode(TaskConstants.EXIT_CODE_FAILURE);
+ logger.error("The current loop thread has been interrupted", e);
+ Thread.currentThread().interrupt();
+ throw new TaskException("The current loop thread has been interrupted");
+ } catch (TaskException ex) {
+ // print the error message with task logger.
+ logger.error("Loop task execute error", ex);
+ setExitStatusCode(TaskConstants.EXIT_CODE_FAILURE);
+ throw ex;
+ } catch (Exception ex) {
+ setExitStatusCode(TaskConstants.EXIT_CODE_FAILURE);
+ logger.error("Loop task execute error", ex);
+ throw new TaskException("Loop task execute error", ex);
+ }
+ }
+
+ /**
+ * Submit the loop task, if submit failed, directly throw exception
+ */
+ public abstract @NonNull LoopTaskInstanceInfo submitLoopTask() throws TaskException;
+
+ /**
+ * Query the loop task status, if query failed, directly throw exception
+ */
+ public abstract @NonNull LoopTaskInstanceStatus queryTaskInstanceStatus(@NonNull LoopTaskInstanceInfo taskInstanceInfo)
+ throws TaskException;
+
+ /**
+ * Get the interval time to query the loop task status
+ */
+ public @NonNull Duration getTaskInstanceStatusQueryInterval() {
+ return TaskConstants.DEFAULT_LOOP_STATUS_INTERVAL;
+ }
+
+ /**
+ * Cancel the loop task, if cancel failed, directly throw exception
+ */
+ public abstract void cancelLoopTaskInstance(@Nullable LoopTaskInstanceInfo taskInstanceInfo) throws TaskException;
+
+ @Override
+ public void cancelApplication(boolean status) throws Exception {
+ cancelLoopTaskInstance(loopTaskInstanceInfo);
+ super.cancelApplication(status);
+ }
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskCancelMethodDefinition.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskCancelMethodDefinition.java
new file mode 100644
index 0000000000..95aa282751
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskCancelMethodDefinition.java
@@ -0,0 +1,26 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop;
+
+import javax.annotation.Nullable;
+
+public interface LoopTaskCancelMethodDefinition extends LoopTaskMethodDefinition {
+
+ void cancelTaskInstance(@Nullable LoopTaskInstanceInfo loopTaskInstanceInfo);
+
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskDefinition.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskDefinition.java
new file mode 100644
index 0000000000..4cf027c00c
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskDefinition.java
@@ -0,0 +1,48 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop;
+
+import lombok.NonNull;
+
+public interface LoopTaskDefinition<SubmitTaskMethodT extends LoopTaskSubmitTaskMethodDefinition,
+ QueryTaskMethodT extends LoopTaskQueryStatusMethodDefinition, CancelTaskMethodT extends LoopTaskCancelMethodDefinition> {
+ /**
+ * The task name of this loop task, e.g: K8sPodTask
+ */
+ @NonNull
+ String getTaskName();
+
+ /**
+ * Submit task method definition, each loop task should contain submit task method.
+ */
+ @NonNull
+ SubmitTaskMethodT getSubmitTaskMethod();
+
+ /**
+ * Query task method definition, each loop task should contain query task method.
+ */
+ @NonNull
+ QueryTaskMethodT getQueryTaskStateMethod();
+
+ /**
+ * Cancel task method definition, each loop task should contain cancel task method, used to cancel the task instance
+ */
+ @NonNull
+ CancelTaskMethodT getCancelTaskMethod();
+
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskInstanceInfo.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskInstanceInfo.java
new file mode 100644
index 0000000000..ec1ac467cb
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskInstanceInfo.java
@@ -0,0 +1,30 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop;
+
+import lombok.NonNull;
+
+/**
+ * The return result of {@link LoopTaskSubmitTaskMethodDefinition#submitLoopTask()},
+ * this can be used to query the task status.
+ */
+public interface LoopTaskInstanceInfo {
+
+ @NonNull
+ String getTaskInstanceId();
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskInstanceStatus.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskInstanceStatus.java
new file mode 100644
index 0000000000..75067023cd
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskInstanceStatus.java
@@ -0,0 +1,29 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop;
+
+/**
+ * The return result of {@link LoopTaskQueryStatusMethodDefinition#queryTaskInstanceStatus(LoopTaskInstanceInfo)}.
+ */
+public interface LoopTaskInstanceStatus {
+ /**
+ * Judge if the task instance is finished.
+ * @return true if the task instance is finished, false otherwise.
+ */
+ boolean isFinished();
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskMethodDefinition.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskMethodDefinition.java
new file mode 100644
index 0000000000..0c0b5067a6
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskMethodDefinition.java
@@ -0,0 +1,26 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop;
+
+import lombok.NonNull;
+
+public interface LoopTaskMethodDefinition {
+ @NonNull
+ LoopTaskMethodType getLoopTaskMethodType();
+
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskMethodType.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskMethodType.java
new file mode 100644
index 0000000000..fc99a5b937
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskMethodType.java
@@ -0,0 +1,23 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop;
+
+public enum LoopTaskMethodType {
+ HTTP,
+ ;
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskQueryStatusMethodDefinition.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskQueryStatusMethodDefinition.java
new file mode 100644
index 0000000000..86d76c3e26
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskQueryStatusMethodDefinition.java
@@ -0,0 +1,34 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop;
+
+import org.apache.dolphinscheduler.plugin.task.api.TaskConstants;
+
+import java.time.Duration;
+
+import lombok.NonNull;
+
+public interface LoopTaskQueryStatusMethodDefinition extends LoopTaskMethodDefinition {
+
+ @NonNull
+ LoopTaskInstanceStatus queryTaskInstanceStatus(@NonNull LoopTaskInstanceInfo taskInstanceInfo);
+
+ default Duration getTaskInstanceStatusQueryInterval() {
+ return TaskConstants.DEFAULT_LOOP_STATUS_INTERVAL;
+ }
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskSubmitTaskMethodDefinition.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskSubmitTaskMethodDefinition.java
new file mode 100644
index 0000000000..b4c4e4b20b
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/LoopTaskSubmitTaskMethodDefinition.java
@@ -0,0 +1,26 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop;
+
+import lombok.NonNull;
+
+public interface LoopTaskSubmitTaskMethodDefinition extends LoopTaskMethodDefinition {
+
+ @NonNull
+ LoopTaskInstanceInfo submitLoopTask();
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/LoopTaskYamlDefinition.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/LoopTaskYamlDefinition.java
new file mode 100644
index 0000000000..2e4582fb1b
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/LoopTaskYamlDefinition.java
@@ -0,0 +1,82 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template;
+
+import java.io.Serializable;
+import java.util.Map;
+
+import lombok.Data;
+
+@Data
+public class LoopTaskYamlDefinition implements Serializable {
+ // todo: support multiple services
+ private LoopTaskServiceYamlDefinition service;
+
+ @Data
+ public static class LoopTaskServiceYamlDefinition implements Serializable {
+ private String name;
+ private String type;
+ private LoopTaskAPIYamlDefinition api;
+ }
+
+ @Data
+ public static class LoopTaskAPIYamlDefinition implements Serializable {
+ private LoopTaskSubmitMethodYamlDefinition submit;
+ private LoopTaskQueryStateYamlDefinition queryState;
+ private LoopTaskCancelYamlDefinition cancel;
+ }
+
+ @Data
+ @SuppressWarnings("checkstyle:ModifierOrder")
+ public static abstract class LoopTaskMethodYamlDefinition {
+ private String url;
+ private String method;
+ private String dataType;
+ private Map<String, String> httpHeaders;
+ private Map<String, Object> requestParams;
+ private Map<String, Object> requestBody;
+ }
+
+ @Data
+ public static class LoopTaskSubmitMethodYamlDefinition extends LoopTaskMethodYamlDefinition {
+
+ /**
+ * Used to extract the given params from the task params.
+ */
+ private Map<String, String> taskParamsExtractJPath;
+
+ /**
+ * Used to extract task instance id from response
+ */
+ private String taskInstanceIdJPath;
+ }
+
+ @Data
+ public static class LoopTaskQueryStateYamlDefinition extends LoopTaskMethodYamlDefinition {
+ /**
+ * Used to extract taskInstance finished state from response
+ * todo: we need to support the function to calculate the finished state
+ */
+ private String taskInstanceFinishedJPath;
+ }
+
+ @Data
+ public static class LoopTaskCancelYamlDefinition extends LoopTaskMethodYamlDefinition {
+ }
+
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/TaskDefinitionParser.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/TaskDefinitionParser.java
new file mode 100644
index 0000000000..d2d61ca8e8
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/TaskDefinitionParser.java
@@ -0,0 +1,32 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template;
+
+import org.apache.dolphinscheduler.plugin.task.api.loop.LoopTaskDefinition;
+
+import lombok.NonNull;
+
+public interface TaskDefinitionParser<TaskDefinitionT extends LoopTaskDefinition<?, ?, ?>> {
+
+ /**
+ * Generate the {@link LoopTaskDefinition} from the given yaml config file.
+ */
+ @NonNull
+ TaskDefinitionT parse(@NonNull String yamlConfigFile);
+
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/TemplateMethodTransformer.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/TemplateMethodTransformer.java
new file mode 100644
index 0000000000..9f09a6c476
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/TemplateMethodTransformer.java
@@ -0,0 +1,32 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template;
+
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.HttpLoopTaskMethodDefinition;
+
+import lombok.NonNull;
+
+public interface TemplateMethodTransformer<YamlMethodT extends LoopTaskYamlDefinition.LoopTaskMethodYamlDefinition,
+ MethodT extends HttpLoopTaskMethodDefinition> {
+
+ /**
+ * Transform the {@link LoopTaskYamlDefinition.LoopTaskMethodYamlDefinition} to {@link HttpLoopTaskMethodDefinition}.
+ */
+ @NonNull
+ MethodT transform(@NonNull YamlMethodT loopTaskAPIYamlDefinition);
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/BaseHttpTemplateLoopTaskExecutor.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/BaseHttpTemplateLoopTaskExecutor.java
new file mode 100644
index 0000000000..de1d3ebe59
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/BaseHttpTemplateLoopTaskExecutor.java
@@ -0,0 +1,57 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template.http;
+
+import org.apache.dolphinscheduler.plugin.task.api.TaskExecutionContext;
+import org.apache.dolphinscheduler.plugin.task.api.loop.BaseLoopTaskExecutor;
+import org.apache.dolphinscheduler.plugin.task.api.loop.LoopTaskInstanceInfo;
+import org.apache.dolphinscheduler.plugin.task.api.loop.LoopTaskInstanceStatus;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.parser.HttpTaskDefinitionParser;
+
+import javax.annotation.Nullable;
+
+import lombok.NonNull;
+
+public abstract class BaseHttpTemplateLoopTaskExecutor extends BaseLoopTaskExecutor {
+
+ private final HttpLoopTaskDefinition httpLoopTaskDefinition;
+
+ public BaseHttpTemplateLoopTaskExecutor(@NonNull TaskExecutionContext taskExecutionContext,
+ @NonNull String taskDefinitionYamlFile) {
+ super(taskExecutionContext);
+ this.httpLoopTaskDefinition = new HttpTaskDefinitionParser().parse(taskDefinitionYamlFile);
+ }
+
+ @Override
+ public @NonNull LoopTaskInstanceInfo submitLoopTask() {
+ return httpLoopTaskDefinition.getSubmitTaskMethod().submitLoopTask();
+ }
+
+ @Override
+ public @NonNull LoopTaskInstanceStatus queryTaskInstanceStatus(@NonNull LoopTaskInstanceInfo taskInstanceInfo) {
+ return httpLoopTaskDefinition.getQueryTaskStateMethod().queryTaskInstanceStatus(taskInstanceInfo);
+ }
+
+ @Override
+ public void cancelLoopTaskInstance(@Nullable LoopTaskInstanceInfo taskInstanceInfo) {
+ if (taskInstanceInfo == null) {
+ return;
+ }
+ httpLoopTaskDefinition.getCancelTaskMethod().cancelTaskInstance(taskInstanceInfo);
+ }
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/HttpLoopTaskDefinition.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/HttpLoopTaskDefinition.java
new file mode 100644
index 0000000000..2d80d5caa1
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/HttpLoopTaskDefinition.java
@@ -0,0 +1,64 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template.http;
+
+import org.apache.dolphinscheduler.plugin.task.api.loop.LoopTaskDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.method.HttpLoopTaskCancelTaskMethodDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.method.HttpLoopTaskQueryStatusMethodDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.method.HttpLoopTaskSubmitTaskMethodDefinition;
+
+import lombok.NonNull;
+
+public class HttpLoopTaskDefinition implements
+ LoopTaskDefinition<HttpLoopTaskSubmitTaskMethodDefinition, HttpLoopTaskQueryStatusMethodDefinition, HttpLoopTaskCancelTaskMethodDefinition> {
+
+ private final String taskName;
+ private final HttpLoopTaskSubmitTaskMethodDefinition submitTaskMethod;
+ private final HttpLoopTaskQueryStatusMethodDefinition queryTaskStateMethod;
+ private final HttpLoopTaskCancelTaskMethodDefinition cancelTaskMethod;
+
+ public HttpLoopTaskDefinition(@NonNull String taskName,
+ @NonNull HttpLoopTaskSubmitTaskMethodDefinition submitTaskMethod,
+ @NonNull HttpLoopTaskQueryStatusMethodDefinition queryTaskStateMethod,
+ @NonNull HttpLoopTaskCancelTaskMethodDefinition cancelTaskMethod) {
+ this.taskName = taskName;
+ this.submitTaskMethod = submitTaskMethod;
+ this.queryTaskStateMethod = queryTaskStateMethod;
+ this.cancelTaskMethod = cancelTaskMethod;
+ }
+
+ @Override
+ public @NonNull String getTaskName() {
+ return taskName;
+ }
+
+ @Override
+ public @NonNull HttpLoopTaskSubmitTaskMethodDefinition getSubmitTaskMethod() {
+ return submitTaskMethod;
+ }
+
+ @Override
+ public @NonNull HttpLoopTaskQueryStatusMethodDefinition getQueryTaskStateMethod() {
+ return queryTaskStateMethod;
+ }
+
+ @Override
+ public @NonNull HttpLoopTaskCancelTaskMethodDefinition getCancelTaskMethod() {
+ return cancelTaskMethod;
+ }
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/HttpLoopTaskInstanceInfo.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/HttpLoopTaskInstanceInfo.java
new file mode 100644
index 0000000000..66507a7131
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/HttpLoopTaskInstanceInfo.java
@@ -0,0 +1,31 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template.http;
+
+import org.apache.dolphinscheduler.plugin.task.api.loop.LoopTaskInstanceInfo;
+
+import lombok.AllArgsConstructor;
+import lombok.Data;
+
+@Data
+@AllArgsConstructor
+public class HttpLoopTaskInstanceInfo implements LoopTaskInstanceInfo {
+
+ private final String taskInstanceId;
+
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/HttpLoopTaskInstanceStatus.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/HttpLoopTaskInstanceStatus.java
new file mode 100644
index 0000000000..1c0c75b473
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/HttpLoopTaskInstanceStatus.java
@@ -0,0 +1,31 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template.http;
+
+import org.apache.dolphinscheduler.plugin.task.api.loop.LoopTaskInstanceStatus;
+
+import lombok.AllArgsConstructor;
+import lombok.Data;
+
+@Data
+@AllArgsConstructor
+public class HttpLoopTaskInstanceStatus implements LoopTaskInstanceStatus {
+
+ private final boolean finished;
+
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/HttpLoopTaskMethodDefinition.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/HttpLoopTaskMethodDefinition.java
new file mode 100644
index 0000000000..d5270863cb
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/HttpLoopTaskMethodDefinition.java
@@ -0,0 +1,43 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template.http;
+
+import org.apache.dolphinscheduler.plugin.task.api.loop.LoopTaskMethodDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.loop.LoopTaskMethodType;
+
+import java.util.Map;
+
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NonNull;
+
+@Data
+@AllArgsConstructor
+public abstract class HttpLoopTaskMethodDefinition implements LoopTaskMethodDefinition {
+ protected final String url;
+ protected final String httpMethodType;
+ protected final String dataType;
+ protected final Map<String, String> httpHeaders;
+ protected final Map<String, Object> requestParams;
+ protected final Map<String, Object> requestBody;
+
+ @Override
+ public @NonNull LoopTaskMethodType getLoopTaskMethodType() {
+ return LoopTaskMethodType.HTTP;
+ }
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/method/HttpLoopTaskCancelTaskMethodDefinition.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/method/HttpLoopTaskCancelTaskMethodDefinition.java
new file mode 100644
index 0000000000..240cc74bfb
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/method/HttpLoopTaskCancelTaskMethodDefinition.java
@@ -0,0 +1,80 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template.http.method;
+
+import org.apache.dolphinscheduler.plugin.task.api.loop.LoopTaskCancelMethodDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.loop.LoopTaskInstanceInfo;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.HttpLoopTaskMethodDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.utils.OkHttpUtils;
+
+import org.apache.commons.lang3.StringUtils;
+
+import java.util.Map;
+
+import javax.annotation.Nullable;
+
+public class HttpLoopTaskCancelTaskMethodDefinition extends HttpLoopTaskMethodDefinition
+ implements LoopTaskCancelMethodDefinition {
+
+ private final String taskInstanceIdHolder = "${taskInstanceId}";
+
+ public HttpLoopTaskCancelTaskMethodDefinition(String url,
+ String httpMethodType,
+ String dataType,
+ Map<String, String> httpHeaders,
+ Map<String, Object> requestParams,
+ Map<String, Object> requestBody) {
+ super(url, httpMethodType, dataType, httpHeaders, requestParams, requestBody);
+ }
+
+ @Override
+ public void cancelTaskInstance(@Nullable LoopTaskInstanceInfo loopTaskInstanceInfo) {
+ if (loopTaskInstanceInfo == null) {
+ return;
+ }
+ if (requestParams != null) {
+ for (Map.Entry<String, Object> entry : requestParams.entrySet()) {
+ if (StringUtils.equals(entry.getValue().toString(), taskInstanceIdHolder)) {
+ entry.setValue(loopTaskInstanceInfo.getTaskInstanceId());
+ }
+ }
+ }
+ if (requestBody != null) {
+ for (Map.Entry<String, Object> entry : requestBody.entrySet()) {
+ if (StringUtils.equalsIgnoreCase(entry.getValue().toString(), taskInstanceIdHolder)) {
+ entry.setValue(loopTaskInstanceInfo.getTaskInstanceId());
+ }
+ }
+ }
+
+ try {
+ if (StringUtils.equalsIgnoreCase("get", httpMethodType)) {
+ OkHttpUtils.get(url, httpHeaders, requestParams);
+ } else if (StringUtils.equalsIgnoreCase("post", httpMethodType)) {
+ OkHttpUtils.post(url, httpHeaders, requestParams, requestBody);
+ } else {
+ throw new IllegalArgumentException(String.format("http method type: %s is not supported",
+ httpMethodType));
+ }
+ } catch (IllegalArgumentException ex) {
+ throw ex;
+ } catch (Exception ex) {
+ throw new RuntimeException("Query loop task instance status failed", ex);
+ }
+ }
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/method/HttpLoopTaskQueryStatusMethodDefinition.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/method/HttpLoopTaskQueryStatusMethodDefinition.java
new file mode 100644
index 0000000000..dbc44a932d
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/method/HttpLoopTaskQueryStatusMethodDefinition.java
@@ -0,0 +1,87 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template.http.method;
+
+import org.apache.dolphinscheduler.plugin.task.api.loop.LoopTaskInstanceInfo;
+import org.apache.dolphinscheduler.plugin.task.api.loop.LoopTaskInstanceStatus;
+import org.apache.dolphinscheduler.plugin.task.api.loop.LoopTaskQueryStatusMethodDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.HttpLoopTaskInstanceStatus;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.HttpLoopTaskMethodDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.utils.JsonPathUtils;
+import org.apache.dolphinscheduler.plugin.task.api.utils.OkHttpUtils;
+
+import org.apache.commons.lang3.StringUtils;
+
+import java.util.Map;
+
+import lombok.NonNull;
+
+public class HttpLoopTaskQueryStatusMethodDefinition extends HttpLoopTaskMethodDefinition
+ implements LoopTaskQueryStatusMethodDefinition {
+
+ private final String taskInstanceFinishedJPath;
+ // inject the taskInstanceId into template
+ private final String taskInstanceIdHolder = "${taskInstanceId}";
+
+ public HttpLoopTaskQueryStatusMethodDefinition(String url,
+ String httpMethodType,
+ String dataType,
+ Map<String, String> httpHeaders,
+ Map<String, Object> requestParams,
+ Map<String, Object> requestBody,
+ String taskInstanceFinishedJPath) {
+ super(url, httpMethodType, dataType, httpHeaders, requestParams, requestBody);
+ this.taskInstanceFinishedJPath = taskInstanceFinishedJPath;
+ }
+
+ @Override
+ public @NonNull LoopTaskInstanceStatus queryTaskInstanceStatus(@NonNull LoopTaskInstanceInfo loopTaskInstanceInfo) {
+ // set the loopTaskInstanceId to request params;
+ if (requestParams != null) {
+ for (Map.Entry<String, Object> entry : requestParams.entrySet()) {
+ if (StringUtils.equals(entry.getValue().toString(), taskInstanceIdHolder)) {
+ entry.setValue(loopTaskInstanceInfo.getTaskInstanceId());
+ }
+ }
+ }
+ if (requestBody != null) {
+ for (Map.Entry<String, Object> entry : requestBody.entrySet()) {
+ if (StringUtils.equalsIgnoreCase(entry.getValue().toString(), taskInstanceIdHolder)) {
+ entry.setValue(loopTaskInstanceInfo.getTaskInstanceId());
+ }
+ }
+ }
+
+ String responseBody;
+ try {
+ if (StringUtils.equalsIgnoreCase("get", httpMethodType)) {
+ responseBody = OkHttpUtils.get(url, httpHeaders, requestParams);
+ } else if (StringUtils.equalsIgnoreCase("post", httpMethodType)) {
+ responseBody = OkHttpUtils.post(url, httpHeaders, requestParams, requestBody);
+ } else {
+ throw new IllegalArgumentException(String.format("http method type: %s is not supported",
+ httpMethodType));
+ }
+ } catch (IllegalArgumentException ex) {
+ throw ex;
+ } catch (Exception ex) {
+ throw new RuntimeException("Query loop task instance status failed", ex);
+ }
+ return new HttpLoopTaskInstanceStatus(JsonPathUtils.exist(responseBody, taskInstanceFinishedJPath));
+ }
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/method/HttpLoopTaskSubmitTaskMethodDefinition.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/method/HttpLoopTaskSubmitTaskMethodDefinition.java
new file mode 100644
index 0000000000..20852a9cb4
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/method/HttpLoopTaskSubmitTaskMethodDefinition.java
@@ -0,0 +1,75 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template.http.method;
+
+import org.apache.dolphinscheduler.plugin.task.api.loop.LoopTaskInstanceInfo;
+import org.apache.dolphinscheduler.plugin.task.api.loop.LoopTaskSubmitTaskMethodDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.HttpLoopTaskInstanceInfo;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.HttpLoopTaskMethodDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.utils.JsonPathUtils;
+import org.apache.dolphinscheduler.plugin.task.api.utils.OkHttpUtils;
+
+import org.apache.commons.lang3.StringUtils;
+
+import java.util.Map;
+import java.util.Optional;
+
+import lombok.NonNull;
+
+public class HttpLoopTaskSubmitTaskMethodDefinition extends HttpLoopTaskMethodDefinition
+ implements LoopTaskSubmitTaskMethodDefinition {
+
+ private final String taskInstanceIdJPath;
+
+ public HttpLoopTaskSubmitTaskMethodDefinition(String url,
+ String httpMethodType,
+ String dataType,
+ Map<String, String> httpHeaders,
+ Map<String, Object> requestParams,
+ Map<String, Object> requestBody,
+ @NonNull String taskInstanceIdJPath) {
+ super(url, httpMethodType, dataType, httpHeaders, requestParams, requestBody);
+ this.taskInstanceIdJPath = taskInstanceIdJPath;
+ }
+
+ @Override
+ public @NonNull LoopTaskInstanceInfo submitLoopTask() {
+ // todo: call http api to submit task
+ String responseBody;
+ try {
+ if (StringUtils.equalsIgnoreCase(httpMethodType, "GET")) {
+ responseBody = OkHttpUtils.get(url, httpHeaders, requestParams);
+ } else if (StringUtils.equalsIgnoreCase(httpMethodType, "POST")) {
+ responseBody = OkHttpUtils.post(url, httpHeaders, requestParams, requestBody);
+ } else {
+ throw new IllegalArgumentException(String.format("The request method type: %s is not supported.",
+ httpMethodType));
+ }
+ } catch (IllegalArgumentException ex) {
+ throw ex;
+ } catch (Exception ex) {
+ throw new RuntimeException("Submit loop task error", ex);
+ }
+ Optional<String> taskInstanceIdOptional = JsonPathUtils.read(responseBody, taskInstanceIdJPath);
+ String taskInstanceId = taskInstanceIdOptional.orElseThrow(() -> new RuntimeException(String.format(
+ "Resolve the taskInstanceId error, responseBody: %s, taskInstanceIdJPath: %s",
+ responseBody,
+ taskInstanceIdJPath)));
+ return new HttpLoopTaskInstanceInfo(taskInstanceId);
+ }
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/parser/CancelTemplateMethodTransformer.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/parser/CancelTemplateMethodTransformer.java
new file mode 100644
index 0000000000..bcc95ba5c7
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/parser/CancelTemplateMethodTransformer.java
@@ -0,0 +1,46 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template.http.parser;
+
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.LoopTaskYamlDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.TemplateMethodTransformer;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.method.HttpLoopTaskCancelTaskMethodDefinition;
+
+import java.util.Map;
+
+import lombok.NonNull;
+
+public class CancelTemplateMethodTransformer implements
+ TemplateMethodTransformer<LoopTaskYamlDefinition.LoopTaskCancelYamlDefinition, HttpLoopTaskCancelTaskMethodDefinition> {
+
+ @Override
+ public @NonNull HttpLoopTaskCancelTaskMethodDefinition transform(@NonNull LoopTaskYamlDefinition.LoopTaskCancelYamlDefinition loopTaskAPIYamlDefinition) {
+ String url = loopTaskAPIYamlDefinition.getUrl();
+ String method = loopTaskAPIYamlDefinition.getMethod();
+ String dataType = loopTaskAPIYamlDefinition.getDataType();
+ Map<String, String> httpHeaders = loopTaskAPIYamlDefinition.getHttpHeaders();
+ Map<String, Object> requestParams = loopTaskAPIYamlDefinition.getRequestParams();
+ Map<String, Object> requestBody = loopTaskAPIYamlDefinition.getRequestBody();
+ return new HttpLoopTaskCancelTaskMethodDefinition(url,
+ method,
+ dataType,
+ httpHeaders,
+ requestParams,
+ requestBody);
+ }
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/parser/HttpTaskDefinitionParser.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/parser/HttpTaskDefinitionParser.java
new file mode 100644
index 0000000000..1bf723736d
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/parser/HttpTaskDefinitionParser.java
@@ -0,0 +1,77 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template.http.parser;
+
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.LoopTaskYamlDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.TaskDefinitionParser;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.HttpLoopTaskDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.method.HttpLoopTaskCancelTaskMethodDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.method.HttpLoopTaskQueryStatusMethodDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.method.HttpLoopTaskSubmitTaskMethodDefinition;
+
+import org.apache.commons.lang3.StringUtils;
+
+import java.io.FileReader;
+import java.io.IOException;
+
+import org.yaml.snakeyaml.Yaml;
+import org.yaml.snakeyaml.constructor.Constructor;
+
+import com.google.common.base.Preconditions;
+
+import lombok.NonNull;
+
+public class HttpTaskDefinitionParser implements TaskDefinitionParser<HttpLoopTaskDefinition> {
+
+ @Override
+ public @NonNull HttpLoopTaskDefinition parse(@NonNull String yamlConfigFile) {
+ LoopTaskYamlDefinition loopTaskYamlDefinition;
+ try {
+ loopTaskYamlDefinition = parseYamlConfigFile(yamlConfigFile);
+ } catch (IOException ex) {
+ throw new IllegalArgumentException(String.format("Parse yaml file: %s error", yamlConfigFile), ex);
+ }
+ validateYamlDefinition(loopTaskYamlDefinition);
+
+ LoopTaskYamlDefinition.LoopTaskServiceYamlDefinition service = loopTaskYamlDefinition.getService();
+ LoopTaskYamlDefinition.LoopTaskAPIYamlDefinition api = service.getApi();
+ HttpLoopTaskSubmitTaskMethodDefinition submitTaskMethod
+ = new SubmitTemplateMethodTransformer().transform(api.getSubmit());
+ HttpLoopTaskQueryStatusMethodDefinition queryTaskStateMethod
+ = new QueryStateTemplateMethodTransformer().transform(api.getQueryState());
+ HttpLoopTaskCancelTaskMethodDefinition cancelTaskMethod
+ = new CancelTemplateMethodTransformer().transform(api.getCancel());
+ return new HttpLoopTaskDefinition(service.getName(), submitTaskMethod, queryTaskStateMethod, cancelTaskMethod);
+ }
+
+ protected @NonNull LoopTaskYamlDefinition parseYamlConfigFile(@NonNull String yamlConfigFile) throws IOException {
+ Yaml yaml = new Yaml(new Constructor(LoopTaskYamlDefinition.class));
+ try (FileReader fileReader = new FileReader(yamlConfigFile)) {
+ return yaml.load(fileReader);
+ }
+ }
+
+ protected void validateYamlDefinition(@NonNull LoopTaskYamlDefinition loopTaskYamlDefinition) {
+ LoopTaskYamlDefinition.LoopTaskServiceYamlDefinition service = loopTaskYamlDefinition.getService();
+ Preconditions.checkNotNull(service, "service is null");
+ Preconditions.checkNotNull(service.getName(), "service name is null");
+ if (!StringUtils.equalsIgnoreCase(service.getType(), "http")) {
+ throw new IllegalArgumentException(String.format("service type: %s is invalidated", service.getType()));
+ }
+ }
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/parser/QueryStateTemplateMethodTransformer.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/parser/QueryStateTemplateMethodTransformer.java
new file mode 100644
index 0000000000..6abd1f2927
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/parser/QueryStateTemplateMethodTransformer.java
@@ -0,0 +1,48 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template.http.parser;
+
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.LoopTaskYamlDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.TemplateMethodTransformer;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.method.HttpLoopTaskQueryStatusMethodDefinition;
+
+import java.util.Map;
+
+import lombok.NonNull;
+
+public class QueryStateTemplateMethodTransformer implements
+ TemplateMethodTransformer<LoopTaskYamlDefinition.LoopTaskQueryStateYamlDefinition, HttpLoopTaskQueryStatusMethodDefinition> {
+
+ @Override
+ public @NonNull HttpLoopTaskQueryStatusMethodDefinition transform(@NonNull LoopTaskYamlDefinition.LoopTaskQueryStateYamlDefinition loopTaskAPIYamlDefinition) {
+ String url = loopTaskAPIYamlDefinition.getUrl();
+ String method = loopTaskAPIYamlDefinition.getMethod();
+ String dataType = loopTaskAPIYamlDefinition.getDataType();
+ Map<String, String> httpHeaders = loopTaskAPIYamlDefinition.getHttpHeaders();
+ Map<String, Object> requestParams = loopTaskAPIYamlDefinition.getRequestParams();
+ Map<String, Object> requestBody = loopTaskAPIYamlDefinition.getRequestBody();
+ String taskInstanceFinishedJPath = loopTaskAPIYamlDefinition.getTaskInstanceFinishedJPath();
+ return new HttpLoopTaskQueryStatusMethodDefinition(url,
+ method,
+ dataType,
+ httpHeaders,
+ requestParams,
+ requestBody,
+ taskInstanceFinishedJPath);
+ }
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/parser/SubmitTemplateMethodTransformer.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/parser/SubmitTemplateMethodTransformer.java
new file mode 100644
index 0000000000..05b476a288
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/parser/SubmitTemplateMethodTransformer.java
@@ -0,0 +1,48 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template.http.parser;
+
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.LoopTaskYamlDefinition;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.TemplateMethodTransformer;
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.http.method.HttpLoopTaskSubmitTaskMethodDefinition;
+
+import java.util.Map;
+
+import lombok.NonNull;
+
+public class SubmitTemplateMethodTransformer implements
+ TemplateMethodTransformer<LoopTaskYamlDefinition.LoopTaskSubmitMethodYamlDefinition, HttpLoopTaskSubmitTaskMethodDefinition> {
+
+ @Override
+ public @NonNull HttpLoopTaskSubmitTaskMethodDefinition transform(@NonNull LoopTaskYamlDefinition.LoopTaskSubmitMethodYamlDefinition loopTaskAPIYamlDefinition) {
+ String url = loopTaskAPIYamlDefinition.getUrl();
+ String method = loopTaskAPIYamlDefinition.getMethod();
+ String dataType = loopTaskAPIYamlDefinition.getDataType();
+ Map<String, String> httpHeaders = loopTaskAPIYamlDefinition.getHttpHeaders();
+ Map<String, Object> requestParams = loopTaskAPIYamlDefinition.getRequestParams();
+ Map<String, Object> requestBody = loopTaskAPIYamlDefinition.getRequestBody();
+ String taskInstanceIdJPath = loopTaskAPIYamlDefinition.getTaskInstanceIdJPath();
+ return new HttpLoopTaskSubmitTaskMethodDefinition(url,
+ method,
+ dataType,
+ httpHeaders,
+ requestParams,
+ requestBody,
+ taskInstanceIdJPath);
+ }
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/utils/JsonPathUtils.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/utils/JsonPathUtils.java
new file mode 100644
index 0000000000..e6e8cb219d
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/utils/JsonPathUtils.java
@@ -0,0 +1,54 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.utils;
+
+import java.util.Optional;
+import java.util.Set;
+
+import com.jayway.jsonpath.JsonPath;
+import com.jayway.jsonpath.Option;
+import com.jayway.jsonpath.internal.DefaultsImpl;
+
+import lombok.NonNull;
+import lombok.experimental.UtilityClass;
+import net.minidev.json.JSONArray;
+
+@UtilityClass
+public class JsonPathUtils {
+
+ static {
+ Set<Option> options = DefaultsImpl.INSTANCE.options();
+ options.add(Option.DEFAULT_PATH_LEAF_TO_NULL);
+ }
+
+ /**
+ * @param jsonString
+ * @param jsonPath
+ * @param <T>
+ * @return
+ */
+ public static <T> Optional<T> read(@NonNull String jsonString, @NonNull String jsonPath) {
+ return Optional.ofNullable(JsonPath.read(jsonString, jsonPath));
+ }
+
+ public static boolean exist(@NonNull String jsonString, @NonNull String jsonPath) {
+ JSONArray jsonArray = JsonPath.read(jsonString, jsonPath);
+ return !jsonArray.isEmpty();
+ }
+
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/utils/OkHttpUtils.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/utils/OkHttpUtils.java
new file mode 100644
index 0000000000..84cfe2a730
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/utils/OkHttpUtils.java
@@ -0,0 +1,99 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.utils;
+
+import org.apache.dolphinscheduler.spi.utils.JSONUtils;
+
+import org.apache.http.HttpStatus;
+
+import java.io.IOException;
+import java.util.Map;
+
+import javax.annotation.Nullable;
+
+import lombok.NonNull;
+import okhttp3.HttpUrl;
+import okhttp3.MediaType;
+import okhttp3.OkHttpClient;
+import okhttp3.Request;
+import okhttp3.RequestBody;
+import okhttp3.Response;
+
+public class OkHttpUtils {
+
+ private static final OkHttpClient CLIENT = new OkHttpClient();
+
+ public static @NonNull String get(@NonNull String url,
+ @Nullable Map<String, String> httpHeaders,
+ @Nullable Map<String, Object> requestParams) throws IOException {
+ String finalUrl = addUrlParams(requestParams, url);
+ Request.Builder requestBuilder = new Request.Builder().url(finalUrl);
+ addHeader(httpHeaders, requestBuilder);
+ Request request = requestBuilder.build();
+ try (Response response = CLIENT.newCall(request).execute()) {
+ return getResponseBody(response);
+ }
+ }
+
+ public static @NonNull String post(@NonNull String url,
+ @Nullable Map<String, String> httpHeaders,
+ @Nullable Map<String, Object> requestParamsMap,
+ @Nullable Map<String, Object> requestBodyMap) throws IOException {
+ String finalUrl = addUrlParams(requestParamsMap, url);
+ Request.Builder requestBuilder = new Request.Builder().url(finalUrl);
+ if (requestBodyMap != null) {
+ requestBuilder = requestBuilder.post(RequestBody.create(MediaType.parse("application/json"),
+ JSONUtils.toJsonString(requestBodyMap)));
+ }
+ try (Response response = CLIENT.newCall(requestBuilder.build()).execute()) {
+ return getResponseBody(response);
+ }
+ }
+
+ private static String addUrlParams(@Nullable Map<String, Object> requestParams, @NonNull String url) {
+ if (requestParams == null) {
+ return url;
+ }
+
+ HttpUrl httpUrl = HttpUrl.parse(url);
+ if (httpUrl == null) {
+ throw new IllegalArgumentException(String.format("url: %s is invalid", url));
+ }
+ HttpUrl.Builder urlBuilder = httpUrl.newBuilder();
+ for (Map.Entry<String, Object> entry : requestParams.entrySet()) {
+ urlBuilder.addQueryParameter(entry.getKey(), entry.getValue().toString());
+ }
+ return urlBuilder.toString();
+ }
+
+ private static void addHeader(@Nullable Map<String, String> headers, @NonNull Request.Builder requestBuilder) {
+ if (headers == null) {
+ return;
+ }
+ headers.forEach(requestBuilder::addHeader);
+ }
+
+ private static String getResponseBody(@NonNull Response response) throws IOException {
+ if (response.code() != HttpStatus.SC_OK || response.body() == null) {
+ throw new RuntimeException(String.format("Request execute failed, httpCode: %s, httpBody: %s",
+ response.code(),
+ response.body()));
+ }
+ return response.body().string();
+ }
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/utils/RetryUtils.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/utils/RetryUtils.java
new file mode 100644
index 0000000000..2dcf3efce4
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/main/java/org/apache/dolphinscheduler/plugin/task/api/utils/RetryUtils.java
@@ -0,0 +1,75 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.utils;
+
+import java.util.function.Supplier;
+
+import lombok.Data;
+import lombok.NonNull;
+import lombok.experimental.UtilityClass;
+
+@UtilityClass
+public class RetryUtils {
+
+ private static final RetryPolicy DEFAULT_RETRY_POLICY = new RetryPolicy(3, 1000L);
+
+ /**
+ * Retry to execute the given function with the default retry policy.
+ */
+ public static <T> T retryFunction(@NonNull Supplier<T> supplier) {
+ return retryFunction(supplier, DEFAULT_RETRY_POLICY);
+ }
+
+ /**
+ * Retry to execute the given function with the given retry policy, the retry policy is used to defined retryTimes and retryInterval.
+ * This method will sleep for retryInterval when execute given supplier failure.
+ */
+ public static <T> T retryFunction(@NonNull Supplier<T> supplier, @NonNull RetryPolicy retryPolicy) {
+ int retryCount = 0;
+ long retryInterval = 0L;
+ while (true) {
+ try {
+ return supplier.get();
+ } catch (Exception ex) {
+ if (retryCount == retryPolicy.getMaxRetryTimes()) {
+ throw ex;
+ }
+ retryCount++;
+ try {
+ Thread.sleep(retryInterval);
+ } catch (InterruptedException e) {
+ Thread.currentThread().interrupt();
+ throw new RuntimeException("The current thread is interrupted, will stop retry", e);
+ }
+ }
+ }
+ }
+
+ @Data
+ public static final class RetryPolicy {
+ /**
+ * The max retry times
+ */
+ private final int maxRetryTimes;
+ /**
+ * The retry interval, if the give function is failed, will sleep the retry interval milliseconds and retry again.
+ */
+ private final long retryInterval;
+
+ }
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/test/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/parser/HttpTaskDefinitionParserTest.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/test/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/parser/HttpTaskDefinitionParserTest.java
new file mode 100644
index 0000000000..71707bfd45
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/test/java/org/apache/dolphinscheduler/plugin/task/api/loop/template/http/parser/HttpTaskDefinitionParserTest.java
@@ -0,0 +1,51 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.loop.template.http.parser;
+
+import org.apache.dolphinscheduler.plugin.task.api.loop.template.LoopTaskYamlDefinition;
+
+import java.io.IOException;
+
+import org.junit.Assert;
+import org.junit.Test;
+
+public class HttpTaskDefinitionParserTest {
+
+ private static final String yamlFile = HttpTaskDefinitionParserTest.class.getResource("/mock_loop_task.yaml")
+ .getFile();
+
+ @Test
+ public void parseYamlConfigFile() throws IOException {
+ LoopTaskYamlDefinition loopTaskYamlDefinition = new HttpTaskDefinitionParser().parseYamlConfigFile(yamlFile);
+ Assert.assertNotNull(loopTaskYamlDefinition);
+ Assert.assertNotNull(loopTaskYamlDefinition.getService());
+ LoopTaskYamlDefinition.LoopTaskServiceYamlDefinition service = loopTaskYamlDefinition.getService();
+ Assert.assertEquals("MockService", service.getName());
+ Assert.assertNotNull(service.getApi());
+ }
+
+ @Test
+ public void validateYamlDefinition() throws IOException {
+ HttpTaskDefinitionParser httpTaskDefinitionParser = new HttpTaskDefinitionParser();
+ LoopTaskYamlDefinition loopTaskYamlDefinition = httpTaskDefinitionParser.parseYamlConfigFile(yamlFile);
+ httpTaskDefinitionParser.validateYamlDefinition(loopTaskYamlDefinition);
+ // if no exception assert true
+ Assert.assertTrue(true);
+
+ }
+}
\ No newline at end of file
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/test/java/org/apache/dolphinscheduler/plugin/task/api/utils/JsonPathUtilsTest.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/test/java/org/apache/dolphinscheduler/plugin/task/api/utils/JsonPathUtilsTest.java
new file mode 100644
index 0000000000..f878beb349
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/test/java/org/apache/dolphinscheduler/plugin/task/api/utils/JsonPathUtilsTest.java
@@ -0,0 +1,40 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.utils;
+
+import java.util.Optional;
+
+import org.junit.Assert;
+import org.junit.Test;
+
+public class JsonPathUtilsTest {
+
+ @Test
+ public void read() {
+ String json = "{\"taskInstanceId\":\"123\",\"taskInstanceFinished\":true}";
+ Optional<Boolean> optionalBoolean = JsonPathUtils.read(json, "$.taskInstanceFinished");
+ Assert.assertTrue(optionalBoolean.get());
+ }
+
+ @Test
+ public void exist() {
+ String json = "{\"taskInstanceId\":\"123\",\"taskInstanceFinished\":true}";
+ Assert.assertTrue(JsonPathUtils.exist(json, "$.[?(@.taskInstanceFinished == true)]"));
+ Assert.assertFalse(JsonPathUtils.exist(json, "$.[?(@.taskInstanceFinished == false)]"));
+ }
+}
\ No newline at end of file
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/test/java/org/apache/dolphinscheduler/plugin/task/api/utils/RetryUtilsTest.java b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/test/java/org/apache/dolphinscheduler/plugin/task/api/utils/RetryUtilsTest.java
new file mode 100644
index 0000000000..a3d6d0f9b8
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/test/java/org/apache/dolphinscheduler/plugin/task/api/utils/RetryUtilsTest.java
@@ -0,0 +1,39 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dolphinscheduler.plugin.task.api.utils;
+
+import java.util.function.Supplier;
+
+import org.junit.Assert;
+import org.junit.Test;
+
+public class RetryUtilsTest {
+
+ @Test(expected = RuntimeException.class)
+ public void retryFunction() {
+ Boolean retrySuccess = RetryUtils.retryFunction(() -> true);
+ Assert.assertTrue(retrySuccess);
+
+ RetryUtils.retryFunction((Supplier<Boolean>) () -> {
+ throw new RuntimeException("Test failed function");
+ });
+ // should throw runtime exception
+ Assert.fail();
+ }
+
+}
diff --git a/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/test/resources/mock_loop_task.yaml b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/test/resources/mock_loop_task.yaml
new file mode 100644
index 0000000000..3f891c805b
--- /dev/null
+++ b/dolphinscheduler-task-plugin/dolphinscheduler-task-api/src/test/resources/mock_loop_task.yaml
@@ -0,0 +1,36 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one or more
+# contributor license agreements. See the NOTICE file distributed with
+# this work for additional information regarding copyright ownership.
+# The ASF licenses this file to You under the Apache License, Version 2.0
+# (the "License"); you may not use this file except in compliance with
+# the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#
+service:
+ name: MockService
+ type: Http
+ api:
+ submit:
+ url: /api/v1/submit
+ method: POST
+ dataType: Json
+ requestParams: { "taskId": "704" }
+ taskInstanceIdJPath: "$.taskInstanceId[0]"
+ queryState:
+ url: /api/v1/state
+ method: GET
+ dataType: Json
+ requestParams: { "runId": "${taskInstanceId}" }
+ cancel:
+ url: /api/v1/cancel
+ method: POST
+ dataType: Json
+ requestParams: { "runId": "${taskInstanceId}" }
diff --git a/tools/dependencies/known-dependencies.txt b/tools/dependencies/known-dependencies.txt
index 49c6d44c7f..60bfb995d3 100755
--- a/tools/dependencies/known-dependencies.txt
+++ b/tools/dependencies/known-dependencies.txt
@@ -266,3 +266,7 @@ websocket-client-9.4.44.v20210927.jar
websocket-common-9.4.44.v20210927.jar
zeppelin-client-0.10.1.jar
zeppelin-common-0.10.1.jar
+json-path-2.7.0.jar
+accessors-smart-2.4.7.jar
+asm-9.1.jar
+json-smart-2.4.7.jar