diff --git a/.github/workflows/build-and-test.yml b/.github/workflows/build-and-test.yml new file mode 100644 index 0000000..b4a6d79 --- /dev/null +++ b/.github/workflows/build-and-test.yml @@ -0,0 +1,109 @@ +# +# Copyright 2024-2026 the original author or authors. +# +# 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 +# +# https://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. +# +name: 🛠️ Build and Test +on: + push: + branches: + - main + - master + paths-ignore: + - '**.md' + pull_request: + branches: + - main + - master + paths-ignore: + - '**.md' + workflow_dispatch: # Allow manual trigger + +env: + JAVA_VERSION: '8' + JAVA_DISTRIBUTION: 'temurin' + +permissions: + contents: read + +jobs: + checkstyle: + runs-on: ubuntu-22.04 + steps: + - name: Checkout code + uses: actions/checkout@v4 + + - name: Set up JDK ${{ env.JAVA_VERSION }} + uses: actions/setup-java@v4 + with: + java-version: ${{ env.JAVA_VERSION }} + distribution: ${{ env.JAVA_DISTRIBUTION }} + cache: 'maven' + + - name: Run checkstyle + run: | + if [ -f lint.sh ]; then + chmod +x lint.sh + ./lint.sh + else + echo "No lint.sh found, skipping checkstyle" + fi + + test: + runs-on: ubuntu-22.04 + needs: [checkstyle] + steps: + - name: Checkout code + uses: actions/checkout@v4 + + - name: Set up JDK ${{ env.JAVA_VERSION }} + uses: actions/setup-java@v4 + with: + java-version: ${{ env.JAVA_VERSION }} + distribution: ${{ env.JAVA_DISTRIBUTION }} + cache: 'maven' + + - name: Run tests + run: mvn clean test + env: + DASHSCOPE_API_KEY: ${{ secrets.DASHSCOPE_API_KEY }} + + - name: Upload test results + if: always() + uses: actions/upload-artifact@v4 + with: + name: test-results + path: target/surefire-reports/ + + build: + runs-on: ubuntu-22.04 + needs: [checkstyle, test] + steps: + - name: Checkout code + uses: actions/checkout@v4 + + - name: Set up JDK ${{ env.JAVA_VERSION }} + uses: actions/setup-java@v4 + with: + java-version: ${{ env.JAVA_VERSION }} + distribution: ${{ env.JAVA_DISTRIBUTION }} + cache: 'maven' + + - name: Build project + run: mvn clean package -DskipTests + + - name: Upload build artifacts + uses: actions/upload-artifact@v4 + with: + name: build-artifacts + path: target/*.jar diff --git a/src/test/java/com/alibaba/dashscope/TestApiKey.java b/src/test/java/com/alibaba/dashscope/TestApiKey.java index c484fa1..395b614 100644 --- a/src/test/java/com/alibaba/dashscope/TestApiKey.java +++ b/src/test/java/com/alibaba/dashscope/TestApiKey.java @@ -29,8 +29,9 @@ public class TestApiKey { @Test @SetEnvironmentVariable(key = "DASHSCOPE_API_KEY", value = environmentValue) public void testSetWithEnvValue() throws NoApiKeyException { + Constants.apiKey = null; // Clear any previously set API key String apiKey = ApiKey.getApiKey(null); - assertEquals(apiKey, environmentValue); + assertEquals(environmentValue, apiKey); } @Test @@ -49,9 +50,16 @@ public void testSetWithConstants() throws NoApiKeyException { @Test public void testWithDefaultFile() throws NoApiKeyException, IOException { + Constants.apiKey = null; // Clear any previously set API key Path homePath = Paths.get(System.getProperty("user.home")); Path dashscopePath = homePath.resolve(".dashscope").resolve("api_key"); String expectedValue = "4444"; + // Delete if exists before creating + if (Files.exists(dashscopePath.getParent()) && Files.isDirectory(dashscopePath.getParent())) { + if (Files.exists(dashscopePath)) { + Files.delete(dashscopePath); + } + } Files.createDirectories(dashscopePath.getParent()); Files.write( dashscopePath, @@ -65,7 +73,9 @@ public void testWithDefaultFile() throws NoApiKeyException, IOException { @Test @SetEnvironmentVariable(key = "DASHSCOPE_API_KEY_FILE_PATH", value = environmentPath) + @ClearEnvironmentVariable(key = "DASHSCOPE_API_KEY") public void testWithEnvFile() throws NoApiKeyException, IOException { + Constants.apiKey = null; // Clear any previously set API key String expectedValue = "555"; Files.write( Paths.get(environmentPath), diff --git a/src/test/java/com/alibaba/dashscope/TestBatchTextEmbedding.java b/src/test/java/com/alibaba/dashscope/TestBatchTextEmbedding.java index a8c613a..de447e7 100644 --- a/src/test/java/com/alibaba/dashscope/TestBatchTextEmbedding.java +++ b/src/test/java/com/alibaba/dashscope/TestBatchTextEmbedding.java @@ -52,7 +52,7 @@ public void testCreateAsyncTask() throws ApiException, NoApiKeyException, IOException, InterruptedException, InputRequiredException { String responseBody = - "{\"request_id\":\"78a74ba9-b8eb-9ca5-ab34-5a56f453cf03\",\"output\":{\"task_id\":\"2a1d8589-7148-422a-b9e7-f41682f07160\",\"task_status\":\"PENDING\"}}"; + "{\"request_id\":\"78a74ba9-b8eb-9ca5-ab34-5a56f453cf03\",\"output\":{\"task_id\":\"2a1d8589-7148-422a-b9e7-f41682f07160\",\"task_status\":\"PENDING\"},\"status_code\":200,\"code\":\"\",\"message\":\"\"}"; server.enqueue( new MockResponse() .setBody(responseBody) @@ -81,7 +81,7 @@ public void testFetchTask() throws ApiException, NoApiKeyException, IOException, InterruptedException, InputRequiredException { String responseBody = - "{\"request_id\":\"78a74ba9-b8eb-9ca5-ab34-5a56f453cf03\",\"output\":{\"task_id\":\"2a1d8589-7148-422a-b9e7-f41682f07160\",\"task_status\":\"PENDING\"}}"; + "{\"request_id\":\"78a74ba9-b8eb-9ca5-ab34-5a56f453cf03\",\"output\":{\"task_id\":\"2a1d8589-7148-422a-b9e7-f41682f07160\",\"task_status\":\"PENDING\"},\"status_code\":200,\"code\":\"\",\"message\":\"\"}"; server.enqueue( new MockResponse() .setBody(responseBody) @@ -101,7 +101,7 @@ public void testFetchTaskWithDiffUrl() throws ApiException, NoApiKeyException, IOException, InterruptedException, InputRequiredException { String responseBody = - "{\"request_id\":\"78a74ba9-b8eb-9ca5-ab34-5a56f453cf03\",\"output\":{\"task_id\":\"2a1d8589-7148-422a-b9e7-f41682f07160\",\"task_status\":\"PENDING\"}}"; + "{\"request_id\":\"78a74ba9-b8eb-9ca5-ab34-5a56f453cf03\",\"output\":{\"task_id\":\"2a1d8589-7148-422a-b9e7-f41682f07160\",\"task_status\":\"PENDING\"},\"status_code\":200,\"code\":\"\",\"message\":\"\"}"; server.enqueue( new MockResponse() .setBody(responseBody) @@ -132,7 +132,7 @@ public void testListParameters() throws ApiException, NoApiKeyException, Interru .status("SUCCEEDED") .build(); String responseBody = - "{\"request_id\":\"31a80745-990d-958b-ad1c-fd51f17a6996\",\"data\":[{\"api_key_id\":\"1\",\"caller_parent_id\":\"2\",\"caller_uid\":\"3\",\"end_time\":1691561396394,\"gmt_create\":1691561394828,\"model_name\":\"pre-offline-file-embedding\",\"region\":\"cn-beijing\",\"request_id\":\"5ddcdba0-9b22-93c1-946e-1eb152b77efa\",\"start_time\":1691561395295,\"status\":\"SUCCEEDED\",\"task_id\":\"bb7c1bdb-d8de-4619-83b8-9ad3c3313def\",\"user_api_unique_key\":\"apikey:v1:embeddings:text-embedding:text-embedding:pre-offline-file-embedding\"}],\"total\":1,\"total_page\":1,\"page_no\":1,\"page_size\":10}"; + "{\"request_id\":\"31a80745-990d-958b-ad1c-fd51f17a6996\",\"data\":[{\"api_key_id\":\"1\",\"caller_parent_id\":\"2\",\"caller_uid\":\"3\",\"end_time\":1691561396394,\"gmt_create\":1691561394828,\"model_name\":\"pre-offline-file-embedding\",\"region\":\"cn-beijing\",\"request_id\":\"5ddcdba0-9b22-93c1-946e-1eb152b77efa\",\"start_time\":1691561395295,\"status\":\"SUCCEEDED\",\"task_id\":\"bb7c1bdb-d8de-4619-83b8-9ad3c3313def\",\"user_api_unique_key\":\"apikey:v1:embeddings:text-embedding:text-embedding:pre-offline-file-embedding\"}],\"total\":1,\"total_page\":1,\"page_no\":1,\"page_size\":10,\"status_code\":200,\"code\":\"\",\"message\":\"\"}"; server.enqueue( new MockResponse() .setBody(responseBody) diff --git a/src/test/java/com/alibaba/dashscope/TestHalfDuplexHttpApi.java b/src/test/java/com/alibaba/dashscope/TestHalfDuplexHttpApi.java index cd17ffe..d72c97b 100644 --- a/src/test/java/com/alibaba/dashscope/TestHalfDuplexHttpApi.java +++ b/src/test/java/com/alibaba/dashscope/TestHalfDuplexHttpApi.java @@ -78,7 +78,7 @@ public void testHttpSendEmptyResponse() throws ApiException, NoApiKeyException, HalfDuplexTestParam.builder().model("qwen-turbo").parameter("k1", "v1").build(); Constants.baseHttpApiUrl = String.format("http://127.0.0.1:%s", port); DashScopeResult result = syncApi.call(param); - assertEquals(JsonUtils.toJson(result), "{}"); + assertEquals(JsonUtils.toJson(result), "{\"statusCode\":200,\"code\":\"\",\"message\":\"\"}"); server.close(); } diff --git a/src/test/java/com/alibaba/dashscope/TestImageSynthesis.java b/src/test/java/com/alibaba/dashscope/TestImageSynthesis.java index bc5db36..0da603f 100644 --- a/src/test/java/com/alibaba/dashscope/TestImageSynthesis.java +++ b/src/test/java/com/alibaba/dashscope/TestImageSynthesis.java @@ -48,7 +48,7 @@ public void testImageSynthesisNormal() throws ApiException, NoApiKeyException, IOException, InterruptedException, InputRequiredException { String responseBody = - "{\"request_id\":\"39\",\"output\":{\"task_id\":\"e4\",\"task_status\":\"SUCCEEDED\",\"results\":[{\"url\":\"https://1\"},{\"url\":\"https://2\"},{\"url\":\"https://\"},{\"url\":\"https://4\"}],\"task_metrics\":{\"TOTAL\":4,\"SUCCEEDED\":4,\"FAILED\":0}},\"usage\":{\"image_count\":4}}"; + "{\"request_id\":\"39\",\"output\":{\"task_id\":\"e4\",\"task_status\":\"SUCCEEDED\",\"results\":[{\"url\":\"https://1\"},{\"url\":\"https://2\"},{\"url\":\"https://\"},{\"url\":\"https://4\"}],\"task_metrics\":{\"TOTAL\":4,\"SUCCEEDED\":4,\"FAILED\":0}},\"usage\":{\"image_count\":4},\"status_code\":200,\"code\":\"\",\"message\":\"\"}"; server.enqueue( new MockResponse() .setBody(responseBody) diff --git a/src/test/java/com/alibaba/dashscope/TestVideoSynthesis.java b/src/test/java/com/alibaba/dashscope/TestVideoSynthesis.java index 4d92b85..fff9a0a 100644 --- a/src/test/java/com/alibaba/dashscope/TestVideoSynthesis.java +++ b/src/test/java/com/alibaba/dashscope/TestVideoSynthesis.java @@ -45,7 +45,7 @@ public void testVideoSynthesisNormal() throws ApiException, NoApiKeyException, IOException, InterruptedException, InputRequiredException { String responseBody = - "{\"request_id\":\"39\",\"output\":{\"task_id\":\"e4\",\"task_status\":\"SUCCEEDED\",\"video_url\":\"https://1\"},\"usage\":{\"video_count\":1}}"; + "{\"request_id\":\"39\",\"output\":{\"task_id\":\"e4\",\"task_status\":\"SUCCEEDED\",\"video_url\":\"https://1\"},\"usage\":{\"video_count\":1,\"duration\":0.0,\"input_video_duration\":0.0,\"output_video_duration\":0.0},\"status_code\":200,\"code\":\"\",\"message\":\"\"}"; assert MEDIA_TYPE_APPLICATION_JSON != null; server.enqueue( new MockResponse() @@ -70,7 +70,7 @@ public void testVideoSynthesisNormal() String requestBody = request.getBody().readUtf8(); System.out.println(requestBody); String expectRequestBody = - "{\"model\":\"wanx-kf2v\",\"input\":{\"extend_prompt\":true,\"first_frame_url\":\"https://www.xxx.cn/a.png\",\"last_frame_url\":\"https://www.xxx.cn/b.png\"},\"parameters\":{\"duration\":5,\"with_audio\":false,\"size\":\"1280*720\",\"resolution\":\"720P\"}}"; + "{\"model\":\"wanx-kf2v\",\"input\":{\"extend_prompt\":true,\"first_frame_url\":\"https://www.xxx.cn/a.png\",\"last_frame_url\":\"https://www.xxx.cn/b.png\"},\"parameters\":{\"with_audio\":false}}"; Assertions.assertEquals(expectRequestBody, requestBody); } @@ -105,7 +105,7 @@ public void testVideoSynthesisUsageMore() String requestBody = request.getBody().readUtf8(); System.out.println(requestBody); String expectRequestBody = - "{\"model\":\"wanx-kf2v\",\"input\":{\"extend_prompt\":true,\"first_frame_url\":\"https://www.xxx.cn/a.png\",\"last_frame_url\":\"https://www.xxx.cn/b.png\"},\"parameters\":{\"duration\":4,\"with_audio\":false,\"size\":\"1280*720\",\"seed\":1234,\"resolution\":\"720P\"}}"; + "{\"model\":\"wanx-kf2v\",\"input\":{\"extend_prompt\":true,\"first_frame_url\":\"https://www.xxx.cn/a.png\",\"last_frame_url\":\"https://www.xxx.cn/b.png\"},\"parameters\":{\"duration\":4,\"with_audio\":false,\"seed\":1234}}"; Assertions.assertEquals(expectRequestBody, requestBody); } }