diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml
index f8d7296..5f92f36 100644
--- a/.github/workflows/ci.yml
+++ b/.github/workflows/ci.yml
@@ -20,10 +20,10 @@ jobs:
if: github.event_name == 'push' || github.event.pull_request.head.repo.fork
steps:
- - uses: actions/checkout@v4
+ - uses: actions/checkout@v6
- name: Set up Java
- uses: actions/setup-java@v4
+ uses: actions/setup-java@v5
with:
distribution: temurin
java-version: |
@@ -40,14 +40,17 @@ jobs:
build:
timeout-minutes: 15
name: build
+ permissions:
+ contents: read
+ id-token: write
runs-on: ${{ github.repository == 'stainless-sdks/alchemyst-ai-sdk-java' && 'depot-ubuntu-24.04' || 'ubuntu-latest' }}
if: github.event_name == 'push' || github.event.pull_request.head.repo.fork
steps:
- - uses: actions/checkout@v4
+ - uses: actions/checkout@v6
- name: Set up Java
- uses: actions/setup-java@v4
+ uses: actions/setup-java@v5
with:
distribution: temurin
java-version: |
@@ -61,16 +64,31 @@ jobs:
- name: Build SDK
run: ./scripts/build
+ - name: Get GitHub OIDC Token
+ if: github.repository == 'stainless-sdks/alchemyst-ai-sdk-java'
+ id: github-oidc
+ uses: actions/github-script@v8
+ with:
+ script: core.setOutput('github_token', await core.getIDToken());
+
+ - name: Build and upload Maven artifacts
+ if: github.repository == 'stainless-sdks/alchemyst-ai-sdk-java'
+ env:
+ URL: https://pkg.stainless.com/s
+ AUTH: ${{ steps.github-oidc.outputs.github_token }}
+ SHA: ${{ github.sha }}
+ PROJECT: alchemyst-ai-sdk-java
+ run: ./scripts/upload-artifacts
test:
timeout-minutes: 15
name: test
runs-on: ${{ github.repository == 'stainless-sdks/alchemyst-ai-sdk-java' && 'depot-ubuntu-24.04' || 'ubuntu-latest' }}
if: github.event_name == 'push' || github.event.pull_request.head.repo.fork
steps:
- - uses: actions/checkout@v4
+ - uses: actions/checkout@v6
- name: Set up Java
- uses: actions/setup-java@v4
+ uses: actions/setup-java@v5
with:
distribution: temurin
java-version: |
diff --git a/.github/workflows/publish-sonatype.yml b/.github/workflows/publish-sonatype.yml
new file mode 100644
index 0000000..6910735
--- /dev/null
+++ b/.github/workflows/publish-sonatype.yml
@@ -0,0 +1,41 @@
+# This workflow is triggered when a GitHub release is created.
+# It can also be run manually to re-publish to Sonatype in case it failed for some reason.
+# You can run this workflow by navigating to https://www.github.com/Alchemyst-ai/alchemyst-sdk-java/actions/workflows/publish-sonatype.yml
+name: Publish Sonatype
+on:
+ workflow_dispatch:
+
+ release:
+ types: [published]
+
+jobs:
+ publish:
+ name: publish
+ runs-on: ubuntu-latest
+
+ steps:
+ - uses: actions/checkout@v6
+
+ - name: Set up Java
+ uses: actions/setup-java@v5
+ with:
+ distribution: temurin
+ java-version: |
+ 8
+ 21
+ cache: gradle
+
+ - name: Set up Gradle
+ uses: gradle/gradle-build-action@v2
+
+ - name: Publish to Sonatype
+ run: |-
+ export -- GPG_SIGNING_KEY_ID
+ printenv -- GPG_SIGNING_KEY | gpg --batch --passphrase-fd 3 --import 3<<< "$GPG_SIGNING_PASSWORD"
+ GPG_SIGNING_KEY_ID="$(gpg --with-colons --list-keys | awk -F : -- '/^pub:/ { getline; print "0x" substr($10, length($10) - 7) }')"
+ ./gradlew publish --no-configuration-cache
+ env:
+ SONATYPE_USERNAME: ${{ secrets.ALCHEMYST_AI_SONATYPE_USERNAME || secrets.SONATYPE_USERNAME }}
+ SONATYPE_PASSWORD: ${{ secrets.ALCHEMYST_AI_SONATYPE_PASSWORD || secrets.SONATYPE_PASSWORD }}
+ GPG_SIGNING_KEY: ${{ secrets.ALCHEMYST_AI_SONATYPE_GPG_SIGNING_KEY || secrets.GPG_SIGNING_KEY }}
+ GPG_SIGNING_PASSWORD: ${{ secrets.ALCHEMYST_AI_SONATYPE_GPG_SIGNING_PASSWORD || secrets.GPG_SIGNING_PASSWORD }}
\ No newline at end of file
diff --git a/.github/workflows/release-doctor.yml b/.github/workflows/release-doctor.yml
new file mode 100644
index 0000000..47f5f3c
--- /dev/null
+++ b/.github/workflows/release-doctor.yml
@@ -0,0 +1,24 @@
+name: Release Doctor
+on:
+ pull_request:
+ branches:
+ - main
+ workflow_dispatch:
+
+jobs:
+ release_doctor:
+ name: release doctor
+ runs-on: ubuntu-latest
+ if: github.repository == 'Alchemyst-ai/alchemyst-sdk-java' && (github.event_name == 'push' || github.event_name == 'workflow_dispatch' || startsWith(github.head_ref, 'release-please') || github.head_ref == 'next')
+
+ steps:
+ - uses: actions/checkout@v6
+
+ - name: Check release environment
+ run: |
+ bash ./bin/check-release-environment
+ env:
+ SONATYPE_USERNAME: ${{ secrets.ALCHEMYST_AI_SONATYPE_USERNAME || secrets.SONATYPE_USERNAME }}
+ SONATYPE_PASSWORD: ${{ secrets.ALCHEMYST_AI_SONATYPE_PASSWORD || secrets.SONATYPE_PASSWORD }}
+ GPG_SIGNING_KEY: ${{ secrets.ALCHEMYST_AI_SONATYPE_GPG_SIGNING_KEY || secrets.GPG_SIGNING_KEY }}
+ GPG_SIGNING_PASSWORD: ${{ secrets.ALCHEMYST_AI_SONATYPE_GPG_SIGNING_PASSWORD || secrets.GPG_SIGNING_PASSWORD }}
diff --git a/.release-please-manifest.json b/.release-please-manifest.json
new file mode 100644
index 0000000..3d2ac0b
--- /dev/null
+++ b/.release-please-manifest.json
@@ -0,0 +1,3 @@
+{
+ ".": "0.1.0"
+}
\ No newline at end of file
diff --git a/.stats.yml b/.stats.yml
index 8b380ed..89f72ef 100644
--- a/.stats.yml
+++ b/.stats.yml
@@ -1,4 +1,4 @@
-configured_endpoints: 11
-openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/alchemyst-ai%2Falchemyst-ai-sdk-cdd0680c6405277f8a47a7d1dcecc54011da8dd3107e02e4600929db8925e76e.yml
-openapi_spec_hash: 2de3999daed6da41616b86f9f1191222
-config_hash: ed5f9a1ea363791f2371dceb218be252
+configured_endpoints: 15
+openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/alchemyst-ai%2Falchemyst-ai-sdk-2f45ad752bad791b73a3ceab084c0a3482ab2f4557e6a8654f3d9d72d34a1255.yml
+openapi_spec_hash: 40c8e2e8d23537e555dc3156e7d14738
+config_hash: 81ab41dc504ce7093b3a81c7e0b5ad9b
diff --git a/CHANGELOG.md b/CHANGELOG.md
new file mode 100644
index 0000000..d4a8403
--- /dev/null
+++ b/CHANGELOG.md
@@ -0,0 +1,53 @@
+# Changelog
+
+## 0.1.0 (2026-01-27)
+
+Full Changelog: [v0.0.1...v0.1.0](https://github.com/Alchemyst-ai/alchemyst-sdk-java/compare/v0.0.1...v0.1.0)
+
+### Features
+
+* **api:** api update ([1ed61b3](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/1ed61b348bd13f2bbf7b55a8025d0fbe287c0d1e))
+* **api:** api update ([c9c5eef](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/c9c5eefd474ea10b3e196f46a8e6858c8a8716eb))
+* **api:** api update ([e6fc759](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/e6fc7595eb7aadbb3afa34f71196b7a2832ac6ee))
+* **api:** api update ([ec854a8](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/ec854a81ce517770c35930bc39802154e19162c6))
+* **api:** api update ([7293a27](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/7293a276f3f20bbf86b42cf4287c7e4eeccdd397))
+* **api:** api update ([8a5700f](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/8a5700f17d0dbca67e0402b9e184e7fbd3aeb91b))
+* **api:** api update ([5355b51](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/5355b5185153bf15461b07678947cb58e8d7f463))
+* **api:** api update ([7bc2e75](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/7bc2e759f0c397b776e83177b885eee4519fff18))
+* **api:** api update ([f2d8572](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/f2d85724db9fe8bb7efa02f8e4c009d995d8d2f0))
+* **api:** api update ([1ad2459](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/1ad2459fa314b04066cc9dde8569d093cdc54347))
+* **api:** api update ([f6b4053](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/f6b4053919d2421f1ff12d76da40dd745a299a07))
+* **api:** api update ([332b173](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/332b17339277c00c0ac550850b7a268eea2076d2))
+* **api:** manual updates ([1a5e991](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/1a5e9914379ef3e1af0622f8a7fd0bc0b1dd4998))
+* **api:** manual updates ([db766aa](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/db766aaac68d34cf82348991e2d6a1d2cf43bfb4))
+* **api:** manual updates ([f60ba30](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/f60ba30d54a67f9543a43717a77e4926866bcc23))
+* **api:** manual updates ([0cfdcfa](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/0cfdcfa52cda6728739dbe9ff351ce63402bfc74))
+* **api:** manual updates ([9fea72a](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/9fea72aa08c955c9f039e250d5fc39b85ea541cb))
+* **api:** manual updates ([952235c](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/952235c34ae4a73cf4ed099a1b63f857ebefcd1c))
+* **api:** manual updates ([f76ba28](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/f76ba28f645f040f38306f12be95071c256a2db7))
+* **client:** allow configuring dispatcher executor service ([65bbbb5](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/65bbbb51be67a7ef854674e9ffc2371c6110fd21))
+
+
+### Bug Fixes
+
+* **client:** cancel okhttp call when future cancelled ([c73093e](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/c73093e2fffc5392b25a405aced8c308ae54a133))
+* **client:** multi-value header serialization ([9653f0d](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/9653f0db5b98ec857eb6566647ebf9d7cdd7e41c))
+
+
+### Chores
+
+* configure new SDK language ([4a05a1a](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/4a05a1a90db6cb8752a0dc67f2fd525475f40cf3))
+* **internal:** codegen related update ([9f9f948](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/9f9f948f5b54a6e83d5c66907e4142e24172f633))
+* **internal:** codegen related update ([fef1b6d](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/fef1b6d56217c58e26efcf354ccfd0b7636a2936))
+* **internal:** codegen related update ([feb242a](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/feb242a1efe3618f84835193af7b48be45f1e774))
+* **internal:** codegen related update ([a2a0c7e](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/a2a0c7ea7fa3674d65f78e2e833195996aaa5d35))
+* **internal:** codegen related update ([a011c38](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/a011c38af4abca2c75d07aeb0db56b76d1398409))
+* **internal:** codegen related update ([8c3c714](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/8c3c71436488deb19eeea9a0d8b9fe2400eae452))
+* **internal:** codegen related update ([079e38c](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/079e38c86b4f66775d59c0dd537d916be1bf0b3b))
+* **internal:** codegen related update ([758020b](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/758020b1f703e97396010ed2aa1bbdbe18522533))
+* update SDK settings ([1c396b2](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/1c396b2879ad0b4c9feab0d8150dcede7d89abb4))
+
+
+### Documentation
+
+* remove `$` for better copy-pasteabality ([87f9cc8](https://github.com/Alchemyst-ai/alchemyst-sdk-java/commit/87f9cc8a86baf0b7167064cdd3ae1ae25aa5f809))
diff --git a/LICENSE b/LICENSE
index dc34e8e..15b3c0f 100644
--- a/LICENSE
+++ b/LICENSE
@@ -186,7 +186,7 @@
same "printed page" as the copyright notice for easier
identification within third-party archives.
- Copyright 2025 Alchemyst AI
+ Copyright 2026 Alchemyst AI
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
diff --git a/README.md b/README.md
index 3df3d9b..a90ebb8 100644
--- a/README.md
+++ b/README.md
@@ -1,20 +1,30 @@
# Alchemyst AI Java API Library
-[](https://central.sonatype.com/artifact/com.alchemystai.sdk/alchemyst-ai-java/0.0.1)
-[](https://javadoc.io/doc/com.alchemystai.sdk/alchemyst-ai-java/0.0.1)
+
-The Alchemyst AI Java SDK provides convenient access to the [Alchemyst AI REST API](https://docs.getalchemystai.com) from applications written in Java.
+[](https://central.sonatype.com/artifact/com.alchemystai.sdk/alchemyst-ai-java/0.1.0)
+[](https://javadoc.io/doc/com.alchemystai.sdk/alchemyst-ai-java/0.1.0)
+
+
+
+The Alchemyst AI Java SDK provides convenient access to the [Alchemyst AI REST API](https://getalchemystai.com/docs) from applications written in Java.
It is generated with [Stainless](https://www.stainless.com/).
-The REST API documentation can be found on [docs.getalchemystai.com](https://docs.getalchemystai.com). Javadocs are available on [javadoc.io](https://javadoc.io/doc/com.alchemystai.sdk/alchemyst-ai-java/0.0.1).
+
+
+The REST API documentation can be found on [getalchemystai.com](https://getalchemystai.com/docs). Javadocs are available on [javadoc.io](https://javadoc.io/doc/com.alchemystai.sdk/alchemyst-ai-java/0.1.0).
+
+
## Installation
+
+
### Gradle
```kotlin
-implementation("com.alchemystai.sdk:alchemyst-ai-java:0.0.1")
+implementation("com.alchemystai.sdk:alchemyst-ai-java:0.1.0")
```
### Maven
@@ -23,10 +33,12 @@ implementation("com.alchemystai.sdk:alchemyst-ai-java:0.0.1")
com.alchemystai.sdk
alchemyst-ai-java
- 0.0.1
+ 0.1.0
```
+
+
## Requirements
This library requires Java 8 or later.
@@ -48,14 +60,14 @@ ContextAddParams params = ContextAddParams.builder()
.addDocument(ContextAddParams.Document.builder()
.content("The content of the document")
.build())
+ .scope(ContextAddParams.Scope.INTERNAL)
+ .source("platform.api.context.add")
.metadata(ContextAddParams.Metadata.builder()
.fileName("notes.txt")
.fileType("text/plain")
.lastModified("2025-10-01T18:42:40.419Z")
.fileSize(1024.0)
.build())
- .scope(ContextAddParams.Scope.INTERNAL)
- .source("platform.api.context.add")
.build();
ContextAddResponse response = client.v1().context().add(params);
```
@@ -160,14 +172,14 @@ ContextAddParams params = ContextAddParams.builder()
.addDocument(ContextAddParams.Document.builder()
.content("The content of the document")
.build())
+ .scope(ContextAddParams.Scope.INTERNAL)
+ .source("platform.api.context.add")
.metadata(ContextAddParams.Metadata.builder()
.fileName("notes.txt")
.fileType("text/plain")
.lastModified("2025-10-01T18:42:40.419Z")
.fileSize(1024.0)
.build())
- .scope(ContextAddParams.Scope.INTERNAL)
- .source("platform.api.context.add")
.build();
CompletableFuture response = client.async().v1().context().add(params);
```
@@ -190,14 +202,14 @@ ContextAddParams params = ContextAddParams.builder()
.addDocument(ContextAddParams.Document.builder()
.content("The content of the document")
.build())
+ .scope(ContextAddParams.Scope.INTERNAL)
+ .source("platform.api.context.add")
.metadata(ContextAddParams.Metadata.builder()
.fileName("notes.txt")
.fileType("text/plain")
.lastModified("2025-10-01T18:42:40.419Z")
.fileSize(1024.0)
.build())
- .scope(ContextAddParams.Scope.INTERNAL)
- .source("platform.api.context.add")
.build();
CompletableFuture response = client.v1().context().add(params);
```
@@ -221,14 +233,14 @@ ContextAddParams params = ContextAddParams.builder()
.addDocument(ContextAddParams.Document.builder()
.content("The content of the document")
.build())
+ .scope(ContextAddParams.Scope.INTERNAL)
+ .source("platform.api.context.add")
.metadata(ContextAddParams.Metadata.builder()
.fileName("notes.txt")
.fileType("text/plain")
.lastModified("2025-10-01T18:42:40.419Z")
.fileSize(1024.0)
.build())
- .scope(ContextAddParams.Scope.INTERNAL)
- .source("platform.api.context.add")
.build();
HttpResponseFor response = client.v1().context().withRawResponse().add(params);
@@ -276,13 +288,13 @@ The SDK uses the standard [OkHttp logging interceptor](https://github.com/square
Enable logging by setting the `ALCHEMYST_AI_LOG` environment variable to `info`:
```sh
-$ export ALCHEMYST_AI_LOG=info
+export ALCHEMYST_AI_LOG=info
```
Or to `debug` for more verbose logging:
```sh
-$ export ALCHEMYST_AI_LOG=debug
+export ALCHEMYST_AI_LOG=debug
```
## ProGuard and R8
@@ -302,6 +314,8 @@ If the SDK threw an exception, but you're _certain_ the version is compatible, t
> [!CAUTION]
> We make no guarantee that the SDK works correctly when the Jackson version check is disabled.
+Also note that there are bugs in older Jackson versions that can affect the SDK. We don't work around all Jackson bugs ([example](https://github.com/FasterXML/jackson-databind/issues/3240)) and expect users to upgrade Jackson for those instead.
+
## Network options
### Retries
@@ -339,7 +353,9 @@ To set a custom timeout, configure the method call using the `timeout` method:
```java
import com.alchemystai.sdk.models.v1.context.ContextAddResponse;
-ContextAddResponse response = client.v1().context().add(RequestOptions.builder().timeout(Duration.ofSeconds(30)).build());
+ContextAddResponse response = client.v1().context().add(
+ params, RequestOptions.builder().timeout(Duration.ofSeconds(30)).build()
+);
```
Or configure the default for all method calls at the client level:
@@ -479,14 +495,14 @@ ContextAddParams params = ContextAddParams.builder()
.addDocument(ContextAddParams.Document.builder()
.content("The content of the document")
.build())
+ .scope(ContextAddParams.Scope.INTERNAL)
+ .source("platform.api.context.add")
.metadata(ContextAddParams.Metadata.builder()
.fileName("notes.txt")
.fileType("text/plain")
.lastModified("2025-10-01T18:42:40.419Z")
.fileSize(1024.0)
.build())
- .scope(ContextAddParams.Scope.INTERNAL)
- .source("platform.api.context.add")
.build();
```
@@ -536,12 +552,12 @@ To forcibly omit a required parameter or property, pass [`JsonMissing`](alchemys
```java
import com.alchemystai.sdk.core.JsonMissing;
import com.alchemystai.sdk.models.v1.context.ContextAddParams;
-import com.alchemystai.sdk.models.v1.context.ContextSearchParams;
-ContextAddParams params = ContextSearchParams.builder()
- .query("search query for user preferences")
- .similarityThreshold(0.8)
- .minimumSimilarityThreshold(JsonMissing.of())
+ContextAddParams params = ContextAddParams.builder()
+ .addDocument(ContextAddParams.Document.builder().build())
+ .scope(ContextAddParams.Scope.INTERNAL)
+ .source("support-inbox")
+ .contextType(JsonMissing.of())
.build();
```
@@ -553,7 +569,7 @@ To access undocumented response properties, call the `_additionalProperties()` m
import com.alchemystai.sdk.core.JsonValue;
import java.util.Map;
-Map additionalProperties = client.v1().context().search(params)._additionalProperties();
+Map additionalProperties = client.v1().context().add(params)._additionalProperties();
JsonValue secretPropertyValue = additionalProperties.get("secretProperty");
String result = secretPropertyValue.accept(new JsonValue.Visitor<>() {
@@ -581,21 +597,22 @@ To access a property's raw JSON value, which may be undocumented, call its `_` p
```java
import com.alchemystai.sdk.core.JsonField;
+import com.alchemystai.sdk.models.v1.context.ContextAddParams;
import java.util.Optional;
-JsonField minimumSimilarityThreshold = client.v1().context().search(params)._minimumSimilarityThreshold();
+JsonField contextType = client.v1().context().add(params)._contextType();
-if (minimumSimilarityThreshold.isMissing()) {
+if (contextType.isMissing()) {
// The property is absent from the JSON response
-} else if (minimumSimilarityThreshold.isNull()) {
+} else if (contextType.isNull()) {
// The property was set to literal null
} else {
// Check if value was provided as a string
// Other methods include `asNumber()`, `asBoolean()`, etc.
- Optional jsonString = minimumSimilarityThreshold.asString();
+ Optional jsonString = contextType.asString();
// Try to deserialize into a custom type
- MyClass myObject = minimumSimilarityThreshold.asUnknown().orElseThrow().convert(MyClass.class);
+ MyClass myObject = contextType.asUnknown().orElseThrow().convert(MyClass.class);
}
```
@@ -608,9 +625,9 @@ By default, the SDK will not throw an exception in this case. It will throw [`Al
If you would prefer to check that the response is completely well-typed upfront, then either call `validate()`:
```java
-import com.alchemystai.sdk.models.v1.context.ContextSearchResponse;
+import com.alchemystai.sdk.models.v1.context.ContextAddResponse;
-ContextSearchResponse response = client.v1().context().search(params).validate();
+ContextAddResponse response = client.v1().context().add(params).validate();
```
Or configure the method call to validate the response using the `responseValidation` method:
@@ -618,7 +635,9 @@ Or configure the method call to validate the response using the `responseValidat
```java
import com.alchemystai.sdk.models.v1.context.ContextAddResponse;
-ContextAddResponse response = client.v1().context().add(RequestOptions.builder().responseValidation(true).build());
+ContextAddResponse response = client.v1().context().add(
+ params, RequestOptions.builder().responseValidation(true).build()
+);
```
Or configure the default for all method calls at the client level:
@@ -671,4 +690,4 @@ This package generally follows [SemVer](https://semver.org/spec/v2.0.0.html) con
We take backwards-compatibility seriously and work hard to ensure you can rely on a smooth upgrade experience.
-We are keen for your feedback; please open an [issue](https://www.github.com/stainless-sdks/alchemyst-ai-sdk-java/issues) with questions, bugs, or suggestions.
+We are keen for your feedback; please open an [issue](https://www.github.com/Alchemyst-ai/alchemyst-sdk-java/issues) with questions, bugs, or suggestions.
diff --git a/alchemyst-ai-java-client-okhttp/build.gradle.kts b/alchemyst-ai-java-client-okhttp/build.gradle.kts
index 61d36f6..cb06679 100644
--- a/alchemyst-ai-java-client-okhttp/build.gradle.kts
+++ b/alchemyst-ai-java-client-okhttp/build.gradle.kts
@@ -11,4 +11,5 @@ dependencies {
testImplementation(kotlin("test"))
testImplementation("org.assertj:assertj-core:3.25.3")
+ testImplementation("com.github.tomakehurst:wiremock-jre8:2.35.2")
}
diff --git a/alchemyst-ai-java-client-okhttp/src/main/kotlin/com/alchemystai/sdk/client/okhttp/AlchemystAiOkHttpClient.kt b/alchemyst-ai-java-client-okhttp/src/main/kotlin/com/alchemystai/sdk/client/okhttp/AlchemystAiOkHttpClient.kt
index efb919f..f31b304 100644
--- a/alchemyst-ai-java-client-okhttp/src/main/kotlin/com/alchemystai/sdk/client/okhttp/AlchemystAiOkHttpClient.kt
+++ b/alchemyst-ai-java-client-okhttp/src/main/kotlin/com/alchemystai/sdk/client/okhttp/AlchemystAiOkHttpClient.kt
@@ -16,6 +16,7 @@ import java.net.Proxy
import java.time.Clock
import java.time.Duration
import java.util.Optional
+import java.util.concurrent.ExecutorService
import javax.net.ssl.HostnameVerifier
import javax.net.ssl.SSLSocketFactory
import javax.net.ssl.X509TrustManager
@@ -44,11 +45,31 @@ class AlchemystAiOkHttpClient private constructor() {
class Builder internal constructor() {
private var clientOptions: ClientOptions.Builder = ClientOptions.builder()
+ private var dispatcherExecutorService: ExecutorService? = null
private var proxy: Proxy? = null
private var sslSocketFactory: SSLSocketFactory? = null
private var trustManager: X509TrustManager? = null
private var hostnameVerifier: HostnameVerifier? = null
+ /**
+ * The executor service to use for running HTTP requests.
+ *
+ * Defaults to OkHttp's
+ * [default executor service](https://github.com/square/okhttp/blob/ace792f443b2ffb17974f5c0d1cecdf589309f26/okhttp/src/commonJvmAndroid/kotlin/okhttp3/Dispatcher.kt#L98-L104).
+ *
+ * This class takes ownership of the executor service and shuts it down when closed.
+ */
+ fun dispatcherExecutorService(dispatcherExecutorService: ExecutorService?) = apply {
+ this.dispatcherExecutorService = dispatcherExecutorService
+ }
+
+ /**
+ * Alias for calling [Builder.dispatcherExecutorService] with
+ * `dispatcherExecutorService.orElse(null)`.
+ */
+ fun dispatcherExecutorService(dispatcherExecutorService: Optional) =
+ dispatcherExecutorService(dispatcherExecutorService.getOrNull())
+
fun proxy(proxy: Proxy?) = apply { this.proxy = proxy }
/** Alias for calling [Builder.proxy] with `proxy.orElse(null)`. */
@@ -299,6 +320,7 @@ class AlchemystAiOkHttpClient private constructor() {
OkHttpClient.builder()
.timeout(clientOptions.timeout())
.proxy(proxy)
+ .dispatcherExecutorService(dispatcherExecutorService)
.sslSocketFactory(sslSocketFactory)
.trustManager(trustManager)
.hostnameVerifier(hostnameVerifier)
diff --git a/alchemyst-ai-java-client-okhttp/src/main/kotlin/com/alchemystai/sdk/client/okhttp/AlchemystAiOkHttpClientAsync.kt b/alchemyst-ai-java-client-okhttp/src/main/kotlin/com/alchemystai/sdk/client/okhttp/AlchemystAiOkHttpClientAsync.kt
index 3eebe95..6d84070 100644
--- a/alchemyst-ai-java-client-okhttp/src/main/kotlin/com/alchemystai/sdk/client/okhttp/AlchemystAiOkHttpClientAsync.kt
+++ b/alchemyst-ai-java-client-okhttp/src/main/kotlin/com/alchemystai/sdk/client/okhttp/AlchemystAiOkHttpClientAsync.kt
@@ -16,6 +16,7 @@ import java.net.Proxy
import java.time.Clock
import java.time.Duration
import java.util.Optional
+import java.util.concurrent.ExecutorService
import javax.net.ssl.HostnameVerifier
import javax.net.ssl.SSLSocketFactory
import javax.net.ssl.X509TrustManager
@@ -44,11 +45,31 @@ class AlchemystAiOkHttpClientAsync private constructor() {
class Builder internal constructor() {
private var clientOptions: ClientOptions.Builder = ClientOptions.builder()
+ private var dispatcherExecutorService: ExecutorService? = null
private var proxy: Proxy? = null
private var sslSocketFactory: SSLSocketFactory? = null
private var trustManager: X509TrustManager? = null
private var hostnameVerifier: HostnameVerifier? = null
+ /**
+ * The executor service to use for running HTTP requests.
+ *
+ * Defaults to OkHttp's
+ * [default executor service](https://github.com/square/okhttp/blob/ace792f443b2ffb17974f5c0d1cecdf589309f26/okhttp/src/commonJvmAndroid/kotlin/okhttp3/Dispatcher.kt#L98-L104).
+ *
+ * This class takes ownership of the executor service and shuts it down when closed.
+ */
+ fun dispatcherExecutorService(dispatcherExecutorService: ExecutorService?) = apply {
+ this.dispatcherExecutorService = dispatcherExecutorService
+ }
+
+ /**
+ * Alias for calling [Builder.dispatcherExecutorService] with
+ * `dispatcherExecutorService.orElse(null)`.
+ */
+ fun dispatcherExecutorService(dispatcherExecutorService: Optional) =
+ dispatcherExecutorService(dispatcherExecutorService.getOrNull())
+
fun proxy(proxy: Proxy?) = apply { this.proxy = proxy }
/** Alias for calling [Builder.proxy] with `proxy.orElse(null)`. */
@@ -299,6 +320,7 @@ class AlchemystAiOkHttpClientAsync private constructor() {
OkHttpClient.builder()
.timeout(clientOptions.timeout())
.proxy(proxy)
+ .dispatcherExecutorService(dispatcherExecutorService)
.sslSocketFactory(sslSocketFactory)
.trustManager(trustManager)
.hostnameVerifier(hostnameVerifier)
diff --git a/alchemyst-ai-java-client-okhttp/src/main/kotlin/com/alchemystai/sdk/client/okhttp/OkHttpClient.kt b/alchemyst-ai-java-client-okhttp/src/main/kotlin/com/alchemystai/sdk/client/okhttp/OkHttpClient.kt
index 42fdef0..1d6b555 100644
--- a/alchemyst-ai-java-client-okhttp/src/main/kotlin/com/alchemystai/sdk/client/okhttp/OkHttpClient.kt
+++ b/alchemyst-ai-java-client-okhttp/src/main/kotlin/com/alchemystai/sdk/client/okhttp/OkHttpClient.kt
@@ -13,12 +13,15 @@ import java.io.IOException
import java.io.InputStream
import java.net.Proxy
import java.time.Duration
+import java.util.concurrent.CancellationException
import java.util.concurrent.CompletableFuture
+import java.util.concurrent.ExecutorService
import javax.net.ssl.HostnameVerifier
import javax.net.ssl.SSLSocketFactory
import javax.net.ssl.X509TrustManager
import okhttp3.Call
import okhttp3.Callback
+import okhttp3.Dispatcher
import okhttp3.HttpUrl.Companion.toHttpUrl
import okhttp3.MediaType
import okhttp3.MediaType.Companion.toMediaType
@@ -29,8 +32,8 @@ import okhttp3.Response
import okhttp3.logging.HttpLoggingInterceptor
import okio.BufferedSink
-class OkHttpClient private constructor(private val okHttpClient: okhttp3.OkHttpClient) :
- HttpClient {
+class OkHttpClient
+private constructor(@JvmSynthetic internal val okHttpClient: okhttp3.OkHttpClient) : HttpClient {
override fun execute(request: HttpRequest, requestOptions: RequestOptions): HttpResponse {
val call = newCall(request, requestOptions)
@@ -50,20 +53,25 @@ class OkHttpClient private constructor(private val okHttpClient: okhttp3.OkHttpC
): CompletableFuture {
val future = CompletableFuture()
- request.body?.run { future.whenComplete { _, _ -> close() } }
-
- newCall(request, requestOptions)
- .enqueue(
- object : Callback {
- override fun onResponse(call: Call, response: Response) {
- future.complete(response.toResponse())
- }
+ val call = newCall(request, requestOptions)
+ call.enqueue(
+ object : Callback {
+ override fun onResponse(call: Call, response: Response) {
+ future.complete(response.toResponse())
+ }
- override fun onFailure(call: Call, e: IOException) {
- future.completeExceptionally(AlchemystAiIoException("Request failed", e))
- }
+ override fun onFailure(call: Call, e: IOException) {
+ future.completeExceptionally(AlchemystAiIoException("Request failed", e))
}
- )
+ }
+ )
+
+ future.whenComplete { _, e ->
+ if (e is CancellationException) {
+ call.cancel()
+ }
+ request.body?.close()
+ }
return future
}
@@ -109,19 +117,19 @@ class OkHttpClient private constructor(private val okHttpClient: okhttp3.OkHttpC
val builder = Request.Builder().url(toUrl()).method(method.name, body)
headers.names().forEach { name ->
- headers.values(name).forEach { builder.header(name, it) }
+ headers.values(name).forEach { builder.addHeader(name, it) }
}
if (
!headers.names().contains("X-Stainless-Read-Timeout") && client.readTimeoutMillis != 0
) {
- builder.header(
+ builder.addHeader(
"X-Stainless-Read-Timeout",
Duration.ofMillis(client.readTimeoutMillis.toLong()).seconds.toString(),
)
}
if (!headers.names().contains("X-Stainless-Timeout") && client.callTimeoutMillis != 0) {
- builder.header(
+ builder.addHeader(
"X-Stainless-Timeout",
Duration.ofMillis(client.callTimeoutMillis.toLong()).seconds.toString(),
)
@@ -192,6 +200,7 @@ class OkHttpClient private constructor(private val okHttpClient: okhttp3.OkHttpC
private var timeout: Timeout = Timeout.default()
private var proxy: Proxy? = null
+ private var dispatcherExecutorService: ExecutorService? = null
private var sslSocketFactory: SSLSocketFactory? = null
private var trustManager: X509TrustManager? = null
private var hostnameVerifier: HostnameVerifier? = null
@@ -202,6 +211,10 @@ class OkHttpClient private constructor(private val okHttpClient: okhttp3.OkHttpC
fun proxy(proxy: Proxy?) = apply { this.proxy = proxy }
+ fun dispatcherExecutorService(dispatcherExecutorService: ExecutorService?) = apply {
+ this.dispatcherExecutorService = dispatcherExecutorService
+ }
+
fun sslSocketFactory(sslSocketFactory: SSLSocketFactory?) = apply {
this.sslSocketFactory = sslSocketFactory
}
@@ -217,12 +230,16 @@ class OkHttpClient private constructor(private val okHttpClient: okhttp3.OkHttpC
fun build(): OkHttpClient =
OkHttpClient(
okhttp3.OkHttpClient.Builder()
+ // `RetryingHttpClient` handles retries if the user enabled them.
+ .retryOnConnectionFailure(false)
.connectTimeout(timeout.connect())
.readTimeout(timeout.read())
.writeTimeout(timeout.write())
.callTimeout(timeout.request())
.proxy(proxy)
.apply {
+ dispatcherExecutorService?.let { dispatcher(Dispatcher(it)) }
+
val sslSocketFactory = sslSocketFactory
val trustManager = trustManager
if (sslSocketFactory != null && trustManager != null) {
diff --git a/alchemyst-ai-java-client-okhttp/src/test/kotlin/com/alchemystai/sdk/client/okhttp/OkHttpClientTest.kt b/alchemyst-ai-java-client-okhttp/src/test/kotlin/com/alchemystai/sdk/client/okhttp/OkHttpClientTest.kt
new file mode 100644
index 0000000..41c0808
--- /dev/null
+++ b/alchemyst-ai-java-client-okhttp/src/test/kotlin/com/alchemystai/sdk/client/okhttp/OkHttpClientTest.kt
@@ -0,0 +1,44 @@
+package com.alchemystai.sdk.client.okhttp
+
+import com.alchemystai.sdk.core.http.HttpMethod
+import com.alchemystai.sdk.core.http.HttpRequest
+import com.github.tomakehurst.wiremock.client.WireMock.*
+import com.github.tomakehurst.wiremock.junit5.WireMockRuntimeInfo
+import com.github.tomakehurst.wiremock.junit5.WireMockTest
+import org.assertj.core.api.Assertions.assertThat
+import org.junit.jupiter.api.BeforeEach
+import org.junit.jupiter.api.Test
+import org.junit.jupiter.api.parallel.ResourceLock
+
+@WireMockTest
+@ResourceLock("https://github.com/wiremock/wiremock/issues/169")
+internal class OkHttpClientTest {
+
+ private lateinit var baseUrl: String
+ private lateinit var httpClient: OkHttpClient
+
+ @BeforeEach
+ fun beforeEach(wmRuntimeInfo: WireMockRuntimeInfo) {
+ baseUrl = wmRuntimeInfo.httpBaseUrl
+ httpClient = OkHttpClient.builder().build()
+ }
+
+ @Test
+ fun executeAsync_whenFutureCancelled_cancelsUnderlyingCall() {
+ stubFor(post(urlPathEqualTo("/something")).willReturn(ok()))
+ val responseFuture =
+ httpClient.executeAsync(
+ HttpRequest.builder()
+ .method(HttpMethod.POST)
+ .baseUrl(baseUrl)
+ .addPathSegment("something")
+ .build()
+ )
+ val call = httpClient.okHttpClient.dispatcher.runningCalls().single()
+
+ responseFuture.cancel(false)
+
+ // Should have cancelled the underlying call
+ assertThat(call.isCanceled()).isTrue()
+ }
+}
diff --git a/alchemyst-ai-java-core/build.gradle.kts b/alchemyst-ai-java-core/build.gradle.kts
index 8b506bc..f8b386b 100644
--- a/alchemyst-ai-java-core/build.gradle.kts
+++ b/alchemyst-ai-java-core/build.gradle.kts
@@ -5,14 +5,16 @@ plugins {
configurations.all {
resolutionStrategy {
- // Compile and test against a lower Jackson version to ensure we're compatible with it.
- // We publish with a higher version (see below) to ensure users depend on a secure version by default.
- force("com.fasterxml.jackson.core:jackson-core:2.13.4")
- force("com.fasterxml.jackson.core:jackson-databind:2.13.4")
- force("com.fasterxml.jackson.core:jackson-annotations:2.13.4")
- force("com.fasterxml.jackson.datatype:jackson-datatype-jdk8:2.13.4")
- force("com.fasterxml.jackson.datatype:jackson-datatype-jsr310:2.13.4")
- force("com.fasterxml.jackson.module:jackson-module-kotlin:2.13.4")
+ // Compile and test against a lower Jackson version to ensure we're compatible with it. Note that
+ // we generally support 2.13.4, but test against 2.14.0 because 2.13.4 has some annoying (but
+ // niche) bugs (users should upgrade if they encounter them). We publish with a higher version
+ // (see below) to ensure users depend on a secure version by default.
+ force("com.fasterxml.jackson.core:jackson-core:2.14.0")
+ force("com.fasterxml.jackson.core:jackson-databind:2.14.0")
+ force("com.fasterxml.jackson.core:jackson-annotations:2.14.0")
+ force("com.fasterxml.jackson.datatype:jackson-datatype-jdk8:2.14.0")
+ force("com.fasterxml.jackson.datatype:jackson-datatype-jsr310:2.14.0")
+ force("com.fasterxml.jackson.module:jackson-module-kotlin:2.14.0")
}
}
diff --git a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/Check.kt b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/Check.kt
index d4478fa..b01d91d 100644
--- a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/Check.kt
+++ b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/Check.kt
@@ -77,7 +77,7 @@ This can happen if you are either:
Double-check that you are depending on compatible Jackson versions.
-See https://www.github.com/stainless-sdks/alchemyst-ai-sdk-java#jackson for more information.
+See https://www.github.com/Alchemyst-ai/alchemyst-sdk-java#jackson for more information.
"""
.trimIndent()
}
diff --git a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/ClientOptions.kt b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/ClientOptions.kt
index 252d193..5a3db81 100644
--- a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/ClientOptions.kt
+++ b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/ClientOptions.kt
@@ -402,6 +402,7 @@ private constructor(
headers.put("X-Stainless-Package-Version", getPackageVersion())
headers.put("X-Stainless-Runtime", "JRE")
headers.put("X-Stainless-Runtime-Version", getJavaVersion())
+ headers.put("X-Stainless-Kotlin-Version", KotlinVersion.CURRENT.toString())
apiKey?.let {
if (!it.isEmpty()) {
headers.put("Authorization", "Bearer $it")
diff --git a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/ObjectMappers.kt b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/ObjectMappers.kt
index 50ca0d0..fc13ae7 100644
--- a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/ObjectMappers.kt
+++ b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/ObjectMappers.kt
@@ -24,7 +24,8 @@ import java.io.InputStream
import java.time.DateTimeException
import java.time.LocalDate
import java.time.LocalDateTime
-import java.time.ZonedDateTime
+import java.time.OffsetDateTime
+import java.time.ZoneId
import java.time.format.DateTimeFormatter
import java.time.temporal.ChronoField
@@ -36,7 +37,7 @@ fun jsonMapper(): JsonMapper =
.addModule(
SimpleModule()
.addSerializer(InputStreamSerializer)
- .addDeserializer(LocalDateTime::class.java, LenientLocalDateTimeDeserializer())
+ .addDeserializer(OffsetDateTime::class.java, LenientOffsetDateTimeDeserializer())
)
.withCoercionConfig(LogicalType.Boolean) {
it.setCoercion(CoercionInputShape.Integer, CoercionAction.Fail)
@@ -47,6 +48,7 @@ fun jsonMapper(): JsonMapper =
}
.withCoercionConfig(LogicalType.Integer) {
it.setCoercion(CoercionInputShape.Boolean, CoercionAction.Fail)
+ .setCoercion(CoercionInputShape.Float, CoercionAction.Fail)
.setCoercion(CoercionInputShape.String, CoercionAction.Fail)
.setCoercion(CoercionInputShape.Array, CoercionAction.Fail)
.setCoercion(CoercionInputShape.Object, CoercionAction.Fail)
@@ -64,6 +66,12 @@ fun jsonMapper(): JsonMapper =
.setCoercion(CoercionInputShape.Array, CoercionAction.Fail)
.setCoercion(CoercionInputShape.Object, CoercionAction.Fail)
}
+ .withCoercionConfig(LogicalType.DateTime) {
+ it.setCoercion(CoercionInputShape.Integer, CoercionAction.Fail)
+ .setCoercion(CoercionInputShape.Float, CoercionAction.Fail)
+ .setCoercion(CoercionInputShape.Array, CoercionAction.Fail)
+ .setCoercion(CoercionInputShape.Object, CoercionAction.Fail)
+ }
.withCoercionConfig(LogicalType.Array) {
it.setCoercion(CoercionInputShape.Boolean, CoercionAction.Fail)
.setCoercion(CoercionInputShape.Integer, CoercionAction.Fail)
@@ -124,10 +132,10 @@ private object InputStreamSerializer : BaseSerializer(InputStream::
}
/**
- * A deserializer that can deserialize [LocalDateTime] from datetimes, dates, and zoned datetimes.
+ * A deserializer that can deserialize [OffsetDateTime] from datetimes, dates, and zoned datetimes.
*/
-private class LenientLocalDateTimeDeserializer :
- StdDeserializer(LocalDateTime::class.java) {
+private class LenientOffsetDateTimeDeserializer :
+ StdDeserializer(OffsetDateTime::class.java) {
companion object {
@@ -141,7 +149,7 @@ private class LenientLocalDateTimeDeserializer :
override fun logicalType(): LogicalType = LogicalType.DateTime
- override fun deserialize(p: JsonParser, context: DeserializationContext?): LocalDateTime {
+ override fun deserialize(p: JsonParser, context: DeserializationContext): OffsetDateTime {
val exceptions = mutableListOf()
for (formatter in DATE_TIME_FORMATTERS) {
@@ -150,17 +158,20 @@ private class LenientLocalDateTimeDeserializer :
return when {
!temporal.isSupported(ChronoField.HOUR_OF_DAY) ->
- LocalDate.from(temporal).atStartOfDay()
+ LocalDate.from(temporal)
+ .atStartOfDay()
+ .atZone(ZoneId.of("UTC"))
+ .toOffsetDateTime()
!temporal.isSupported(ChronoField.OFFSET_SECONDS) ->
- LocalDateTime.from(temporal)
- else -> ZonedDateTime.from(temporal).toLocalDateTime()
+ LocalDateTime.from(temporal).atZone(ZoneId.of("UTC")).toOffsetDateTime()
+ else -> OffsetDateTime.from(temporal)
}
} catch (e: DateTimeException) {
exceptions.add(e)
}
}
- throw JsonParseException(p, "Cannot parse `LocalDateTime` from value: ${p.text}").apply {
+ throw JsonParseException(p, "Cannot parse `OffsetDateTime` from value: ${p.text}").apply {
exceptions.forEach { addSuppressed(it) }
}
}
diff --git a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/http/HttpRequest.kt b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/http/HttpRequest.kt
index 04d9342..96b71d6 100644
--- a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/http/HttpRequest.kt
+++ b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/http/HttpRequest.kt
@@ -2,6 +2,7 @@ package com.alchemystai.sdk.core.http
import com.alchemystai.sdk.core.checkRequired
import com.alchemystai.sdk.core.toImmutable
+import java.net.URLEncoder
class HttpRequest
private constructor(
@@ -13,6 +14,35 @@ private constructor(
@get:JvmName("body") val body: HttpRequestBody?,
) {
+ fun url(): String = buildString {
+ append(baseUrl)
+
+ pathSegments.forEach { segment ->
+ if (!endsWith("/")) {
+ append("/")
+ }
+ append(URLEncoder.encode(segment, "UTF-8"))
+ }
+
+ if (queryParams.isEmpty()) {
+ return@buildString
+ }
+
+ append("?")
+ var isFirst = true
+ queryParams.keys().forEach { key ->
+ queryParams.values(key).forEach { value ->
+ if (!isFirst) {
+ append("&")
+ }
+ append(URLEncoder.encode(key, "UTF-8"))
+ append("=")
+ append(URLEncoder.encode(value, "UTF-8"))
+ isFirst = false
+ }
+ }
+ }
+
fun toBuilder(): Builder = Builder().from(this)
override fun toString(): String =
diff --git a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/http/RetryingHttpClient.kt b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/http/RetryingHttpClient.kt
index 13936be..a9a03cc 100644
--- a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/http/RetryingHttpClient.kt
+++ b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/core/http/RetryingHttpClient.kt
@@ -31,10 +31,6 @@ private constructor(
) : HttpClient {
override fun execute(request: HttpRequest, requestOptions: RequestOptions): HttpResponse {
- if (!isRetryable(request) || maxRetries <= 0) {
- return httpClient.execute(request, requestOptions)
- }
-
var modifiedRequest = maybeAddIdempotencyHeader(request)
// Don't send the current retry count in the headers if the caller set their own value.
@@ -48,6 +44,10 @@ private constructor(
modifiedRequest = setRetryCountHeader(modifiedRequest, retries)
}
+ if (!isRetryable(modifiedRequest)) {
+ return httpClient.execute(modifiedRequest, requestOptions)
+ }
+
val response =
try {
val response = httpClient.execute(modifiedRequest, requestOptions)
@@ -75,10 +75,6 @@ private constructor(
request: HttpRequest,
requestOptions: RequestOptions,
): CompletableFuture {
- if (!isRetryable(request) || maxRetries <= 0) {
- return httpClient.executeAsync(request, requestOptions)
- }
-
val modifiedRequest = maybeAddIdempotencyHeader(request)
// Don't send the current retry count in the headers if the caller set their own value.
@@ -94,8 +90,12 @@ private constructor(
val requestWithRetryCount =
if (shouldSendRetryCount) setRetryCountHeader(request, retries) else request
- return httpClient
- .executeAsync(requestWithRetryCount, requestOptions)
+ val responseFuture = httpClient.executeAsync(requestWithRetryCount, requestOptions)
+ if (!isRetryable(requestWithRetryCount)) {
+ return responseFuture
+ }
+
+ return responseFuture
.handleAsync(
fun(
response: HttpResponse?,
diff --git a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextAddParams.kt b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextAddParams.kt
index f6ab212..aa8092c 100644
--- a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextAddParams.kt
+++ b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextAddParams.kt
@@ -9,6 +9,7 @@ import com.alchemystai.sdk.core.JsonMissing
import com.alchemystai.sdk.core.JsonValue
import com.alchemystai.sdk.core.Params
import com.alchemystai.sdk.core.checkKnown
+import com.alchemystai.sdk.core.checkRequired
import com.alchemystai.sdk.core.http.Headers
import com.alchemystai.sdk.core.http.QueryParams
import com.alchemystai.sdk.core.toImmutable
@@ -36,42 +37,42 @@ private constructor(
/**
* Type of context being added
*
- * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if the
- * server responded with an unexpected value).
+ * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type or is
+ * unexpectedly missing or null (e.g. if the server responded with an unexpected value).
*/
- fun contextType(): Optional = body.contextType()
+ fun contextType(): ContextType = body.contextType()
/**
* Array of documents with content and additional metadata
*
- * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if the
- * server responded with an unexpected value).
+ * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type or is
+ * unexpectedly missing or null (e.g. if the server responded with an unexpected value).
*/
- fun documents(): Optional> = body.documents()
+ fun documents(): List = body.documents()
/**
- * Additional metadata for the context
+ * Scope of the context
*
- * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if the
- * server responded with an unexpected value).
+ * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type or is
+ * unexpectedly missing or null (e.g. if the server responded with an unexpected value).
*/
- fun metadata(): Optional = body.metadata()
+ fun scope(): Scope = body.scope()
/**
- * Scope of the context
+ * The source of the context data
*
- * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if the
- * server responded with an unexpected value).
+ * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type or is
+ * unexpectedly missing or null (e.g. if the server responded with an unexpected value).
*/
- fun scope(): Optional = body.scope()
+ fun source(): String = body.source()
/**
- * The source of the context data
+ * Additional metadata for the context
*
* @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if the
* server responded with an unexpected value).
*/
- fun source(): Optional = body.source()
+ fun metadata(): Optional = body.metadata()
/**
* Returns the raw JSON value of [contextType].
@@ -87,13 +88,6 @@ private constructor(
*/
fun _documents(): JsonField> = body._documents()
- /**
- * Returns the raw JSON value of [metadata].
- *
- * Unlike [metadata], this method doesn't throw if the JSON field has an unexpected type.
- */
- fun _metadata(): JsonField = body._metadata()
-
/**
* Returns the raw JSON value of [scope].
*
@@ -108,6 +102,13 @@ private constructor(
*/
fun _source(): JsonField = body._source()
+ /**
+ * Returns the raw JSON value of [metadata].
+ *
+ * Unlike [metadata], this method doesn't throw if the JSON field has an unexpected type.
+ */
+ fun _metadata(): JsonField = body._metadata()
+
fun _additionalBodyProperties(): Map = body._additionalProperties()
/** Additional headers to send with the request. */
@@ -120,9 +121,17 @@ private constructor(
companion object {
- @JvmStatic fun none(): ContextAddParams = builder().build()
-
- /** Returns a mutable builder for constructing an instance of [ContextAddParams]. */
+ /**
+ * Returns a mutable builder for constructing an instance of [ContextAddParams].
+ *
+ * The following fields are required:
+ * ```java
+ * .contextType()
+ * .documents()
+ * .scope()
+ * .source()
+ * ```
+ */
@JvmStatic fun builder() = Builder()
}
@@ -147,9 +156,9 @@ private constructor(
* Otherwise, it's more convenient to use the top-level setters instead:
* - [contextType]
* - [documents]
- * - [metadata]
* - [scope]
* - [source]
+ * - [metadata]
* - etc.
*/
fun body(body: Body) = apply { this.body = body.toBuilder() }
@@ -187,18 +196,6 @@ private constructor(
*/
fun addDocument(document: Document) = apply { body.addDocument(document) }
- /** Additional metadata for the context */
- fun metadata(metadata: Metadata) = apply { body.metadata(metadata) }
-
- /**
- * Sets [Builder.metadata] to an arbitrary JSON value.
- *
- * You should usually call [Builder.metadata] with a well-typed [Metadata] value instead.
- * This method is primarily for setting the field to an undocumented or not yet supported
- * value.
- */
- fun metadata(metadata: JsonField) = apply { body.metadata(metadata) }
-
/** Scope of the context */
fun scope(scope: Scope) = apply { body.scope(scope) }
@@ -221,6 +218,18 @@ private constructor(
*/
fun source(source: JsonField) = apply { body.source(source) }
+ /** Additional metadata for the context */
+ fun metadata(metadata: Metadata) = apply { body.metadata(metadata) }
+
+ /**
+ * Sets [Builder.metadata] to an arbitrary JSON value.
+ *
+ * You should usually call [Builder.metadata] with a well-typed [Metadata] value instead.
+ * This method is primarily for setting the field to an undocumented or not yet supported
+ * value.
+ */
+ fun metadata(metadata: JsonField) = apply { body.metadata(metadata) }
+
fun additionalBodyProperties(additionalBodyProperties: Map) = apply {
body.additionalProperties(additionalBodyProperties)
}
@@ -342,6 +351,16 @@ private constructor(
* Returns an immutable instance of [ContextAddParams].
*
* Further updates to this [Builder] will not mutate the returned instance.
+ *
+ * The following fields are required:
+ * ```java
+ * .contextType()
+ * .documents()
+ * .scope()
+ * .source()
+ * ```
+ *
+ * @throws IllegalStateException if any required field is unset.
*/
fun build(): ContextAddParams =
ContextAddParams(body.build(), additionalHeaders.build(), additionalQueryParams.build())
@@ -358,9 +377,9 @@ private constructor(
private constructor(
private val contextType: JsonField,
private val documents: JsonField>,
- private val metadata: JsonField,
private val scope: JsonField,
private val source: JsonField,
+ private val metadata: JsonField,
private val additionalProperties: MutableMap,
) {
@@ -372,52 +391,52 @@ private constructor(
@JsonProperty("documents")
@ExcludeMissing
documents: JsonField> = JsonMissing.of(),
+ @JsonProperty("scope") @ExcludeMissing scope: JsonField = JsonMissing.of(),
+ @JsonProperty("source") @ExcludeMissing source: JsonField = JsonMissing.of(),
@JsonProperty("metadata")
@ExcludeMissing
metadata: JsonField = JsonMissing.of(),
- @JsonProperty("scope") @ExcludeMissing scope: JsonField = JsonMissing.of(),
- @JsonProperty("source") @ExcludeMissing source: JsonField = JsonMissing.of(),
- ) : this(contextType, documents, metadata, scope, source, mutableMapOf())
+ ) : this(contextType, documents, scope, source, metadata, mutableMapOf())
/**
* Type of context being added
*
- * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if
- * the server responded with an unexpected value).
+ * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type or is
+ * unexpectedly missing or null (e.g. if the server responded with an unexpected value).
*/
- fun contextType(): Optional = contextType.getOptional("context_type")
+ fun contextType(): ContextType = contextType.getRequired("context_type")
/**
* Array of documents with content and additional metadata
*
- * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if
- * the server responded with an unexpected value).
+ * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type or is
+ * unexpectedly missing or null (e.g. if the server responded with an unexpected value).
*/
- fun documents(): Optional> = documents.getOptional("documents")
+ fun documents(): List = documents.getRequired("documents")
/**
- * Additional metadata for the context
+ * Scope of the context
*
- * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if
- * the server responded with an unexpected value).
+ * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type or is
+ * unexpectedly missing or null (e.g. if the server responded with an unexpected value).
*/
- fun metadata(): Optional = metadata.getOptional("metadata")
+ fun scope(): Scope = scope.getRequired("scope")
/**
- * Scope of the context
+ * The source of the context data
*
- * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if
- * the server responded with an unexpected value).
+ * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type or is
+ * unexpectedly missing or null (e.g. if the server responded with an unexpected value).
*/
- fun scope(): Optional = scope.getOptional("scope")
+ fun source(): String = source.getRequired("source")
/**
- * The source of the context data
+ * Additional metadata for the context
*
* @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if
* the server responded with an unexpected value).
*/
- fun source(): Optional = source.getOptional("source")
+ fun metadata(): Optional = metadata.getOptional("metadata")
/**
* Returns the raw JSON value of [contextType].
@@ -437,13 +456,6 @@ private constructor(
@ExcludeMissing
fun _documents(): JsonField> = documents
- /**
- * Returns the raw JSON value of [metadata].
- *
- * Unlike [metadata], this method doesn't throw if the JSON field has an unexpected type.
- */
- @JsonProperty("metadata") @ExcludeMissing fun _metadata(): JsonField = metadata
-
/**
* Returns the raw JSON value of [scope].
*
@@ -458,6 +470,13 @@ private constructor(
*/
@JsonProperty("source") @ExcludeMissing fun _source(): JsonField = source
+ /**
+ * Returns the raw JSON value of [metadata].
+ *
+ * Unlike [metadata], this method doesn't throw if the JSON field has an unexpected type.
+ */
+ @JsonProperty("metadata") @ExcludeMissing fun _metadata(): JsonField = metadata
+
@JsonAnySetter
private fun putAdditionalProperty(key: String, value: JsonValue) {
additionalProperties.put(key, value)
@@ -472,27 +491,37 @@ private constructor(
companion object {
- /** Returns a mutable builder for constructing an instance of [Body]. */
+ /**
+ * Returns a mutable builder for constructing an instance of [Body].
+ *
+ * The following fields are required:
+ * ```java
+ * .contextType()
+ * .documents()
+ * .scope()
+ * .source()
+ * ```
+ */
@JvmStatic fun builder() = Builder()
}
/** A builder for [Body]. */
class Builder internal constructor() {
- private var contextType: JsonField = JsonMissing.of()
+ private var contextType: JsonField? = null
private var documents: JsonField>? = null
+ private var scope: JsonField? = null
+ private var source: JsonField? = null
private var metadata: JsonField = JsonMissing.of()
- private var scope: JsonField = JsonMissing.of()
- private var source: JsonField = JsonMissing.of()
private var additionalProperties: MutableMap = mutableMapOf()
@JvmSynthetic
internal fun from(body: Body) = apply {
contextType = body.contextType
documents = body.documents.map { it.toMutableList() }
- metadata = body.metadata
scope = body.scope
source = body.source
+ metadata = body.metadata
additionalProperties = body.additionalProperties.toMutableMap()
}
@@ -536,18 +565,6 @@ private constructor(
}
}
- /** Additional metadata for the context */
- fun metadata(metadata: Metadata) = metadata(JsonField.of(metadata))
-
- /**
- * Sets [Builder.metadata] to an arbitrary JSON value.
- *
- * You should usually call [Builder.metadata] with a well-typed [Metadata] value
- * instead. This method is primarily for setting the field to an undocumented or not yet
- * supported value.
- */
- fun metadata(metadata: JsonField) = apply { this.metadata = metadata }
-
/** Scope of the context */
fun scope(scope: Scope) = scope(JsonField.of(scope))
@@ -572,6 +589,18 @@ private constructor(
*/
fun source(source: JsonField) = apply { this.source = source }
+ /** Additional metadata for the context */
+ fun metadata(metadata: Metadata) = metadata(JsonField.of(metadata))
+
+ /**
+ * Sets [Builder.metadata] to an arbitrary JSON value.
+ *
+ * You should usually call [Builder.metadata] with a well-typed [Metadata] value
+ * instead. This method is primarily for setting the field to an undocumented or not yet
+ * supported value.
+ */
+ fun metadata(metadata: JsonField) = apply { this.metadata = metadata }
+
fun additionalProperties(additionalProperties: Map) = apply {
this.additionalProperties.clear()
putAllAdditionalProperties(additionalProperties)
@@ -595,14 +624,24 @@ private constructor(
* Returns an immutable instance of [Body].
*
* Further updates to this [Builder] will not mutate the returned instance.
+ *
+ * The following fields are required:
+ * ```java
+ * .contextType()
+ * .documents()
+ * .scope()
+ * .source()
+ * ```
+ *
+ * @throws IllegalStateException if any required field is unset.
*/
fun build(): Body =
Body(
- contextType,
- (documents ?: JsonMissing.of()).map { it.toImmutable() },
+ checkRequired("contextType", contextType),
+ checkRequired("documents", documents).map { it.toImmutable() },
+ checkRequired("scope", scope),
+ checkRequired("source", source),
metadata,
- scope,
- source,
additionalProperties.toMutableMap(),
)
}
@@ -614,11 +653,11 @@ private constructor(
return@apply
}
- contextType().ifPresent { it.validate() }
- documents().ifPresent { it.forEach { it.validate() } }
- metadata().ifPresent { it.validate() }
- scope().ifPresent { it.validate() }
+ contextType().validate()
+ documents().forEach { it.validate() }
+ scope().validate()
source()
+ metadata().ifPresent { it.validate() }
validated = true
}
@@ -640,9 +679,9 @@ private constructor(
internal fun validity(): Int =
(contextType.asKnown().getOrNull()?.validity() ?: 0) +
(documents.asKnown().getOrNull()?.sumOf { it.validity().toInt() } ?: 0) +
- (metadata.asKnown().getOrNull()?.validity() ?: 0) +
(scope.asKnown().getOrNull()?.validity() ?: 0) +
- (if (source.asKnown().isPresent) 1 else 0)
+ (if (source.asKnown().isPresent) 1 else 0) +
+ (metadata.asKnown().getOrNull()?.validity() ?: 0)
override fun equals(other: Any?): Boolean {
if (this === other) {
@@ -652,20 +691,20 @@ private constructor(
return other is Body &&
contextType == other.contextType &&
documents == other.documents &&
- metadata == other.metadata &&
scope == other.scope &&
source == other.source &&
+ metadata == other.metadata &&
additionalProperties == other.additionalProperties
}
private val hashCode: Int by lazy {
- Objects.hash(contextType, documents, metadata, scope, source, additionalProperties)
+ Objects.hash(contextType, documents, scope, source, metadata, additionalProperties)
}
override fun hashCode(): Int = hashCode
override fun toString() =
- "Body{contextType=$contextType, documents=$documents, metadata=$metadata, scope=$scope, source=$source, additionalProperties=$additionalProperties}"
+ "Body{contextType=$contextType, documents=$documents, scope=$scope, source=$source, metadata=$metadata, additionalProperties=$additionalProperties}"
}
/** Type of context being added */
@@ -946,6 +985,134 @@ private constructor(
"Document{content=$content, additionalProperties=$additionalProperties}"
}
+ /** Scope of the context */
+ class Scope @JsonCreator private constructor(private val value: JsonField) : Enum {
+
+ /**
+ * Returns this class instance's raw value.
+ *
+ * This is usually only useful if this instance was deserialized from data that doesn't
+ * match any known member, and you want to know that value. For example, if the SDK is on an
+ * older version than the API, then the API may respond with new members that the SDK is
+ * unaware of.
+ */
+ @com.fasterxml.jackson.annotation.JsonValue fun _value(): JsonField = value
+
+ companion object {
+
+ @JvmField val INTERNAL = of("internal")
+
+ @JvmField val EXTERNAL = of("external")
+
+ @JvmStatic fun of(value: String) = Scope(JsonField.of(value))
+ }
+
+ /** An enum containing [Scope]'s known values. */
+ enum class Known {
+ INTERNAL,
+ EXTERNAL,
+ }
+
+ /**
+ * An enum containing [Scope]'s known values, as well as an [_UNKNOWN] member.
+ *
+ * An instance of [Scope] can contain an unknown value in a couple of cases:
+ * - It was deserialized from data that doesn't match any known member. For example, if the
+ * SDK is on an older version than the API, then the API may respond with new members that
+ * the SDK is unaware of.
+ * - It was constructed with an arbitrary value using the [of] method.
+ */
+ enum class Value {
+ INTERNAL,
+ EXTERNAL,
+ /** An enum member indicating that [Scope] was instantiated with an unknown value. */
+ _UNKNOWN,
+ }
+
+ /**
+ * Returns an enum member corresponding to this class instance's value, or [Value._UNKNOWN]
+ * if the class was instantiated with an unknown value.
+ *
+ * Use the [known] method instead if you're certain the value is always known or if you want
+ * to throw for the unknown case.
+ */
+ fun value(): Value =
+ when (this) {
+ INTERNAL -> Value.INTERNAL
+ EXTERNAL -> Value.EXTERNAL
+ else -> Value._UNKNOWN
+ }
+
+ /**
+ * Returns an enum member corresponding to this class instance's value.
+ *
+ * Use the [value] method instead if you're uncertain the value is always known and don't
+ * want to throw for the unknown case.
+ *
+ * @throws AlchemystAiInvalidDataException if this class instance's value is a not a known
+ * member.
+ */
+ fun known(): Known =
+ when (this) {
+ INTERNAL -> Known.INTERNAL
+ EXTERNAL -> Known.EXTERNAL
+ else -> throw AlchemystAiInvalidDataException("Unknown Scope: $value")
+ }
+
+ /**
+ * Returns this class instance's primitive wire representation.
+ *
+ * This differs from the [toString] method because that method is primarily for debugging
+ * and generally doesn't throw.
+ *
+ * @throws AlchemystAiInvalidDataException if this class instance's value does not have the
+ * expected primitive type.
+ */
+ fun asString(): String =
+ _value().asString().orElseThrow {
+ AlchemystAiInvalidDataException("Value is not a String")
+ }
+
+ private var validated: Boolean = false
+
+ fun validate(): Scope = apply {
+ if (validated) {
+ return@apply
+ }
+
+ known()
+ validated = true
+ }
+
+ fun isValid(): Boolean =
+ try {
+ validate()
+ true
+ } catch (e: AlchemystAiInvalidDataException) {
+ false
+ }
+
+ /**
+ * Returns a score indicating how many valid values are contained in this object
+ * recursively.
+ *
+ * Used for best match union deserialization.
+ */
+ @JvmSynthetic internal fun validity(): Int = if (value() == Value._UNKNOWN) 0 else 1
+
+ override fun equals(other: Any?): Boolean {
+ if (this === other) {
+ return true
+ }
+
+ return other is Scope && value == other.value
+ }
+
+ override fun hashCode() = value.hashCode()
+
+ override fun toString() = value.toString()
+ }
+
/** Additional metadata for the context */
class Metadata
@JsonCreator(mode = JsonCreator.Mode.DISABLED)
@@ -1274,134 +1441,6 @@ private constructor(
"Metadata{fileName=$fileName, fileSize=$fileSize, fileType=$fileType, groupName=$groupName, lastModified=$lastModified, additionalProperties=$additionalProperties}"
}
- /** Scope of the context */
- class Scope @JsonCreator private constructor(private val value: JsonField) : Enum {
-
- /**
- * Returns this class instance's raw value.
- *
- * This is usually only useful if this instance was deserialized from data that doesn't
- * match any known member, and you want to know that value. For example, if the SDK is on an
- * older version than the API, then the API may respond with new members that the SDK is
- * unaware of.
- */
- @com.fasterxml.jackson.annotation.JsonValue fun _value(): JsonField = value
-
- companion object {
-
- @JvmField val INTERNAL = of("internal")
-
- @JvmField val EXTERNAL = of("external")
-
- @JvmStatic fun of(value: String) = Scope(JsonField.of(value))
- }
-
- /** An enum containing [Scope]'s known values. */
- enum class Known {
- INTERNAL,
- EXTERNAL,
- }
-
- /**
- * An enum containing [Scope]'s known values, as well as an [_UNKNOWN] member.
- *
- * An instance of [Scope] can contain an unknown value in a couple of cases:
- * - It was deserialized from data that doesn't match any known member. For example, if the
- * SDK is on an older version than the API, then the API may respond with new members that
- * the SDK is unaware of.
- * - It was constructed with an arbitrary value using the [of] method.
- */
- enum class Value {
- INTERNAL,
- EXTERNAL,
- /** An enum member indicating that [Scope] was instantiated with an unknown value. */
- _UNKNOWN,
- }
-
- /**
- * Returns an enum member corresponding to this class instance's value, or [Value._UNKNOWN]
- * if the class was instantiated with an unknown value.
- *
- * Use the [known] method instead if you're certain the value is always known or if you want
- * to throw for the unknown case.
- */
- fun value(): Value =
- when (this) {
- INTERNAL -> Value.INTERNAL
- EXTERNAL -> Value.EXTERNAL
- else -> Value._UNKNOWN
- }
-
- /**
- * Returns an enum member corresponding to this class instance's value.
- *
- * Use the [value] method instead if you're uncertain the value is always known and don't
- * want to throw for the unknown case.
- *
- * @throws AlchemystAiInvalidDataException if this class instance's value is a not a known
- * member.
- */
- fun known(): Known =
- when (this) {
- INTERNAL -> Known.INTERNAL
- EXTERNAL -> Known.EXTERNAL
- else -> throw AlchemystAiInvalidDataException("Unknown Scope: $value")
- }
-
- /**
- * Returns this class instance's primitive wire representation.
- *
- * This differs from the [toString] method because that method is primarily for debugging
- * and generally doesn't throw.
- *
- * @throws AlchemystAiInvalidDataException if this class instance's value does not have the
- * expected primitive type.
- */
- fun asString(): String =
- _value().asString().orElseThrow {
- AlchemystAiInvalidDataException("Value is not a String")
- }
-
- private var validated: Boolean = false
-
- fun validate(): Scope = apply {
- if (validated) {
- return@apply
- }
-
- known()
- validated = true
- }
-
- fun isValid(): Boolean =
- try {
- validate()
- true
- } catch (e: AlchemystAiInvalidDataException) {
- false
- }
-
- /**
- * Returns a score indicating how many valid values are contained in this object
- * recursively.
- *
- * Used for best match union deserialization.
- */
- @JvmSynthetic internal fun validity(): Int = if (value() == Value._UNKNOWN) 0 else 1
-
- override fun equals(other: Any?): Boolean {
- if (this === other) {
- return true
- }
-
- return other is Scope && value == other.value
- }
-
- override fun hashCode() = value.hashCode()
-
- override fun toString() = value.toString()
- }
-
override fun equals(other: Any?): Boolean {
if (this === other) {
return true
diff --git a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextAddResponse.kt b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextAddResponse.kt
index 6bc83f7..767b1ad 100644
--- a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextAddResponse.kt
+++ b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextAddResponse.kt
@@ -3,19 +3,79 @@
package com.alchemystai.sdk.models.v1.context
import com.alchemystai.sdk.core.ExcludeMissing
+import com.alchemystai.sdk.core.JsonField
+import com.alchemystai.sdk.core.JsonMissing
import com.alchemystai.sdk.core.JsonValue
+import com.alchemystai.sdk.core.checkRequired
import com.alchemystai.sdk.errors.AlchemystAiInvalidDataException
import com.fasterxml.jackson.annotation.JsonAnyGetter
import com.fasterxml.jackson.annotation.JsonAnySetter
import com.fasterxml.jackson.annotation.JsonCreator
+import com.fasterxml.jackson.annotation.JsonProperty
import java.util.Collections
import java.util.Objects
+import java.util.Optional
class ContextAddResponse
@JsonCreator(mode = JsonCreator.Mode.DISABLED)
-private constructor(private val additionalProperties: MutableMap) {
+private constructor(
+ private val contextId: JsonField,
+ private val success: JsonField,
+ private val processedDocuments: JsonField,
+ private val additionalProperties: MutableMap,
+) {
+
+ @JsonCreator
+ private constructor(
+ @JsonProperty("context_id") @ExcludeMissing contextId: JsonField = JsonMissing.of(),
+ @JsonProperty("success") @ExcludeMissing success: JsonField = JsonMissing.of(),
+ @JsonProperty("processed_documents")
+ @ExcludeMissing
+ processedDocuments: JsonField = JsonMissing.of(),
+ ) : this(contextId, success, processedDocuments, mutableMapOf())
- @JsonCreator private constructor() : this(mutableMapOf())
+ /**
+ * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type or is
+ * unexpectedly missing or null (e.g. if the server responded with an unexpected value).
+ */
+ fun contextId(): String = contextId.getRequired("context_id")
+
+ /**
+ * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type or is
+ * unexpectedly missing or null (e.g. if the server responded with an unexpected value).
+ */
+ fun success(): Boolean = success.getRequired("success")
+
+ /**
+ * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if the
+ * server responded with an unexpected value).
+ */
+ fun processedDocuments(): Optional =
+ processedDocuments.getOptional("processed_documents")
+
+ /**
+ * Returns the raw JSON value of [contextId].
+ *
+ * Unlike [contextId], this method doesn't throw if the JSON field has an unexpected type.
+ */
+ @JsonProperty("context_id") @ExcludeMissing fun _contextId(): JsonField = contextId
+
+ /**
+ * Returns the raw JSON value of [success].
+ *
+ * Unlike [success], this method doesn't throw if the JSON field has an unexpected type.
+ */
+ @JsonProperty("success") @ExcludeMissing fun _success(): JsonField = success
+
+ /**
+ * Returns the raw JSON value of [processedDocuments].
+ *
+ * Unlike [processedDocuments], this method doesn't throw if the JSON field has an unexpected
+ * type.
+ */
+ @JsonProperty("processed_documents")
+ @ExcludeMissing
+ fun _processedDocuments(): JsonField = processedDocuments
@JsonAnySetter
private fun putAdditionalProperty(key: String, value: JsonValue) {
@@ -31,20 +91,69 @@ private constructor(private val additionalProperties: MutableMap? = null
+ private var success: JsonField? = null
+ private var processedDocuments: JsonField = JsonMissing.of()
private var additionalProperties: MutableMap = mutableMapOf()
@JvmSynthetic
internal fun from(contextAddResponse: ContextAddResponse) = apply {
+ contextId = contextAddResponse.contextId
+ success = contextAddResponse.success
+ processedDocuments = contextAddResponse.processedDocuments
additionalProperties = contextAddResponse.additionalProperties.toMutableMap()
}
+ fun contextId(contextId: String) = contextId(JsonField.of(contextId))
+
+ /**
+ * Sets [Builder.contextId] to an arbitrary JSON value.
+ *
+ * You should usually call [Builder.contextId] with a well-typed [String] value instead.
+ * This method is primarily for setting the field to an undocumented or not yet supported
+ * value.
+ */
+ fun contextId(contextId: JsonField) = apply { this.contextId = contextId }
+
+ fun success(success: Boolean) = success(JsonField.of(success))
+
+ /**
+ * Sets [Builder.success] to an arbitrary JSON value.
+ *
+ * You should usually call [Builder.success] with a well-typed [Boolean] value instead. This
+ * method is primarily for setting the field to an undocumented or not yet supported value.
+ */
+ fun success(success: JsonField) = apply { this.success = success }
+
+ fun processedDocuments(processedDocuments: Double) =
+ processedDocuments(JsonField.of(processedDocuments))
+
+ /**
+ * Sets [Builder.processedDocuments] to an arbitrary JSON value.
+ *
+ * You should usually call [Builder.processedDocuments] with a well-typed [Double] value
+ * instead. This method is primarily for setting the field to an undocumented or not yet
+ * supported value.
+ */
+ fun processedDocuments(processedDocuments: JsonField) = apply {
+ this.processedDocuments = processedDocuments
+ }
+
fun additionalProperties(additionalProperties: Map) = apply {
this.additionalProperties.clear()
putAllAdditionalProperties(additionalProperties)
@@ -68,8 +177,22 @@ private constructor(private val additionalProperties: MutableMap = body.byId()
/**
- * Optional organization ID
+ * Optional user ID
*
* @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if the
* server responded with an unexpected value).
*/
- fun organizationId(): Optional = body.organizationId()
+ @Deprecated("deprecated") fun userId(): Optional = body.userId()
/**
- * Source identifier for the context
+ * Returns the raw JSON value of [organizationId].
*
- * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if the
- * server responded with an unexpected value).
+ * Unlike [organizationId], this method doesn't throw if the JSON field has an unexpected type.
*/
- fun source(): Optional = body.source()
+ fun _organizationId(): JsonField = body._organizationId()
/**
- * Optional user ID
+ * Returns the raw JSON value of [source].
*
- * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if the
- * server responded with an unexpected value).
+ * Unlike [source], this method doesn't throw if the JSON field has an unexpected type.
*/
- fun userId(): Optional = body.userId()
+ fun _source(): JsonField = body._source()
/**
* Returns the raw JSON value of [byDoc].
@@ -81,26 +99,12 @@ private constructor(
*/
fun _byId(): JsonField = body._byId()
- /**
- * Returns the raw JSON value of [organizationId].
- *
- * Unlike [organizationId], this method doesn't throw if the JSON field has an unexpected type.
- */
- fun _organizationId(): JsonField = body._organizationId()
-
- /**
- * Returns the raw JSON value of [source].
- *
- * Unlike [source], this method doesn't throw if the JSON field has an unexpected type.
- */
- fun _source(): JsonField = body._source()
-
/**
* Returns the raw JSON value of [userId].
*
* Unlike [userId], this method doesn't throw if the JSON field has an unexpected type.
*/
- fun _userId(): JsonField = body._userId()
+ @Deprecated("deprecated") fun _userId(): JsonField = body._userId()
fun _additionalBodyProperties(): Map = body._additionalProperties()
@@ -114,9 +118,15 @@ private constructor(
companion object {
- @JvmStatic fun none(): ContextDeleteParams = builder().build()
-
- /** Returns a mutable builder for constructing an instance of [ContextDeleteParams]. */
+ /**
+ * Returns a mutable builder for constructing an instance of [ContextDeleteParams].
+ *
+ * The following fields are required:
+ * ```java
+ * .organizationId()
+ * .source()
+ * ```
+ */
@JvmStatic fun builder() = Builder()
}
@@ -139,15 +149,40 @@ private constructor(
*
* This is generally only useful if you are already constructing the body separately.
* Otherwise, it's more convenient to use the top-level setters instead:
- * - [byDoc]
- * - [byId]
* - [organizationId]
* - [source]
+ * - [byDoc]
+ * - [byId]
* - [userId]
* - etc.
*/
fun body(body: Body) = apply { this.body = body.toBuilder() }
+ /** Organization ID */
+ fun organizationId(organizationId: String) = apply { body.organizationId(organizationId) }
+
+ /**
+ * Sets [Builder.organizationId] to an arbitrary JSON value.
+ *
+ * You should usually call [Builder.organizationId] with a well-typed [String] value
+ * instead. This method is primarily for setting the field to an undocumented or not yet
+ * supported value.
+ */
+ fun organizationId(organizationId: JsonField) = apply {
+ body.organizationId(organizationId)
+ }
+
+ /** Source identifier for the context */
+ fun source(source: String) = apply { body.source(source) }
+
+ /**
+ * Sets [Builder.source] to an arbitrary JSON value.
+ *
+ * You should usually call [Builder.source] with a well-typed [String] value instead. This
+ * method is primarily for setting the field to an undocumented or not yet supported value.
+ */
+ fun source(source: JsonField) = apply { body.source(source) }
+
/** Flag to delete by document */
fun byDoc(byDoc: Boolean?) = apply { body.byDoc(byDoc) }
@@ -190,40 +225,11 @@ private constructor(
*/
fun byId(byId: JsonField) = apply { body.byId(byId) }
- /** Optional organization ID */
- fun organizationId(organizationId: String?) = apply { body.organizationId(organizationId) }
-
- /** Alias for calling [Builder.organizationId] with `organizationId.orElse(null)`. */
- fun organizationId(organizationId: Optional) =
- organizationId(organizationId.getOrNull())
-
- /**
- * Sets [Builder.organizationId] to an arbitrary JSON value.
- *
- * You should usually call [Builder.organizationId] with a well-typed [String] value
- * instead. This method is primarily for setting the field to an undocumented or not yet
- * supported value.
- */
- fun organizationId(organizationId: JsonField) = apply {
- body.organizationId(organizationId)
- }
-
- /** Source identifier for the context */
- fun source(source: String) = apply { body.source(source) }
-
- /**
- * Sets [Builder.source] to an arbitrary JSON value.
- *
- * You should usually call [Builder.source] with a well-typed [String] value instead. This
- * method is primarily for setting the field to an undocumented or not yet supported value.
- */
- fun source(source: JsonField) = apply { body.source(source) }
-
/** Optional user ID */
- fun userId(userId: String?) = apply { body.userId(userId) }
+ @Deprecated("deprecated") fun userId(userId: String?) = apply { body.userId(userId) }
/** Alias for calling [Builder.userId] with `userId.orElse(null)`. */
- fun userId(userId: Optional) = userId(userId.getOrNull())
+ @Deprecated("deprecated") fun userId(userId: Optional) = userId(userId.getOrNull())
/**
* Sets [Builder.userId] to an arbitrary JSON value.
@@ -231,6 +237,7 @@ private constructor(
* You should usually call [Builder.userId] with a well-typed [String] value instead. This
* method is primarily for setting the field to an undocumented or not yet supported value.
*/
+ @Deprecated("deprecated")
fun userId(userId: JsonField) = apply { body.userId(userId) }
fun additionalBodyProperties(additionalBodyProperties: Map) = apply {
@@ -354,6 +361,14 @@ private constructor(
* Returns an immutable instance of [ContextDeleteParams].
*
* Further updates to this [Builder] will not mutate the returned instance.
+ *
+ * The following fields are required:
+ * ```java
+ * .organizationId()
+ * .source()
+ * ```
+ *
+ * @throws IllegalStateException if any required field is unset.
*/
fun build(): ContextDeleteParams =
ContextDeleteParams(
@@ -372,56 +387,56 @@ private constructor(
class Body
@JsonCreator(mode = JsonCreator.Mode.DISABLED)
private constructor(
- private val byDoc: JsonField,
- private val byId: JsonField,
private val organizationId: JsonField,
private val source: JsonField,
+ private val byDoc: JsonField,
+ private val byId: JsonField,
private val userId: JsonField,
private val additionalProperties: MutableMap,
) {
@JsonCreator
private constructor(
- @JsonProperty("by_doc") @ExcludeMissing byDoc: JsonField = JsonMissing.of(),
- @JsonProperty("by_id") @ExcludeMissing byId: JsonField = JsonMissing.of(),
@JsonProperty("organization_id")
@ExcludeMissing
organizationId: JsonField = JsonMissing.of(),
@JsonProperty("source") @ExcludeMissing source: JsonField = JsonMissing.of(),
+ @JsonProperty("by_doc") @ExcludeMissing byDoc: JsonField = JsonMissing.of(),
+ @JsonProperty("by_id") @ExcludeMissing byId: JsonField = JsonMissing.of(),
@JsonProperty("user_id") @ExcludeMissing userId: JsonField = JsonMissing.of(),
- ) : this(byDoc, byId, organizationId, source, userId, mutableMapOf())
+ ) : this(organizationId, source, byDoc, byId, userId, mutableMapOf())
/**
- * Flag to delete by document
+ * Organization ID
*
- * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if
- * the server responded with an unexpected value).
+ * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type or is
+ * unexpectedly missing or null (e.g. if the server responded with an unexpected value).
*/
- fun byDoc(): Optional = byDoc.getOptional("by_doc")
+ fun organizationId(): String = organizationId.getRequired("organization_id")
/**
- * Flag to delete by ID
+ * Source identifier for the context
*
- * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if
- * the server responded with an unexpected value).
+ * @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type or is
+ * unexpectedly missing or null (e.g. if the server responded with an unexpected value).
*/
- fun byId(): Optional = byId.getOptional("by_id")
+ fun source(): String = source.getRequired("source")
/**
- * Optional organization ID
+ * Flag to delete by document
*
* @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if
* the server responded with an unexpected value).
*/
- fun organizationId(): Optional = organizationId.getOptional("organization_id")
+ fun byDoc(): Optional = byDoc.getOptional("by_doc")
/**
- * Source identifier for the context
+ * Flag to delete by ID
*
* @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if
* the server responded with an unexpected value).
*/
- fun source(): Optional = source.getOptional("source")
+ fun byId(): Optional = byId.getOptional("by_id")
/**
* Optional user ID
@@ -429,21 +444,7 @@ private constructor(
* @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if
* the server responded with an unexpected value).
*/
- fun userId(): Optional = userId.getOptional("user_id")
-
- /**
- * Returns the raw JSON value of [byDoc].
- *
- * Unlike [byDoc], this method doesn't throw if the JSON field has an unexpected type.
- */
- @JsonProperty("by_doc") @ExcludeMissing fun _byDoc(): JsonField = byDoc
-
- /**
- * Returns the raw JSON value of [byId].
- *
- * Unlike [byId], this method doesn't throw if the JSON field has an unexpected type.
- */
- @JsonProperty("by_id") @ExcludeMissing fun _byId(): JsonField = byId
+ @Deprecated("deprecated") fun userId(): Optional = userId.getOptional("user_id")
/**
* Returns the raw JSON value of [organizationId].
@@ -462,12 +463,29 @@ private constructor(
*/
@JsonProperty("source") @ExcludeMissing fun _source(): JsonField = source
+ /**
+ * Returns the raw JSON value of [byDoc].
+ *
+ * Unlike [byDoc], this method doesn't throw if the JSON field has an unexpected type.
+ */
+ @JsonProperty("by_doc") @ExcludeMissing fun _byDoc(): JsonField = byDoc
+
+ /**
+ * Returns the raw JSON value of [byId].
+ *
+ * Unlike [byId], this method doesn't throw if the JSON field has an unexpected type.
+ */
+ @JsonProperty("by_id") @ExcludeMissing fun _byId(): JsonField = byId
+
/**
* Returns the raw JSON value of [userId].
*
* Unlike [userId], this method doesn't throw if the JSON field has an unexpected type.
*/
- @JsonProperty("user_id") @ExcludeMissing fun _userId(): JsonField = userId
+ @Deprecated("deprecated")
+ @JsonProperty("user_id")
+ @ExcludeMissing
+ fun _userId(): JsonField = userId
@JsonAnySetter
private fun putAdditionalProperty(key: String, value: JsonValue) {
@@ -483,30 +501,65 @@ private constructor(
companion object {
- /** Returns a mutable builder for constructing an instance of [Body]. */
+ /**
+ * Returns a mutable builder for constructing an instance of [Body].
+ *
+ * The following fields are required:
+ * ```java
+ * .organizationId()
+ * .source()
+ * ```
+ */
@JvmStatic fun builder() = Builder()
}
/** A builder for [Body]. */
class Builder internal constructor() {
+ private var organizationId: JsonField? = null
+ private var source: JsonField? = null
private var byDoc: JsonField = JsonMissing.of()
private var byId: JsonField = JsonMissing.of()
- private var organizationId: JsonField = JsonMissing.of()
- private var source: JsonField = JsonMissing.of()
private var userId: JsonField = JsonMissing.of()
private var additionalProperties: MutableMap = mutableMapOf()
@JvmSynthetic
internal fun from(body: Body) = apply {
- byDoc = body.byDoc
- byId = body.byId
organizationId = body.organizationId
source = body.source
+ byDoc = body.byDoc
+ byId = body.byId
userId = body.userId
additionalProperties = body.additionalProperties.toMutableMap()
}
+ /** Organization ID */
+ fun organizationId(organizationId: String) =
+ organizationId(JsonField.of(organizationId))
+
+ /**
+ * Sets [Builder.organizationId] to an arbitrary JSON value.
+ *
+ * You should usually call [Builder.organizationId] with a well-typed [String] value
+ * instead. This method is primarily for setting the field to an undocumented or not yet
+ * supported value.
+ */
+ fun organizationId(organizationId: JsonField) = apply {
+ this.organizationId = organizationId
+ }
+
+ /** Source identifier for the context */
+ fun source(source: String) = source(JsonField.of(source))
+
+ /**
+ * Sets [Builder.source] to an arbitrary JSON value.
+ *
+ * You should usually call [Builder.source] with a well-typed [String] value instead.
+ * This method is primarily for setting the field to an undocumented or not yet
+ * supported value.
+ */
+ fun source(source: JsonField) = apply { this.source = source }
+
/** Flag to delete by document */
fun byDoc(byDoc: Boolean?) = byDoc(JsonField.ofNullable(byDoc))
@@ -551,41 +604,12 @@ private constructor(
*/
fun byId(byId: JsonField) = apply { this.byId = byId }
- /** Optional organization ID */
- fun organizationId(organizationId: String?) =
- organizationId(JsonField.ofNullable(organizationId))
-
- /** Alias for calling [Builder.organizationId] with `organizationId.orElse(null)`. */
- fun organizationId(organizationId: Optional) =
- organizationId(organizationId.getOrNull())
-
- /**
- * Sets [Builder.organizationId] to an arbitrary JSON value.
- *
- * You should usually call [Builder.organizationId] with a well-typed [String] value
- * instead. This method is primarily for setting the field to an undocumented or not yet
- * supported value.
- */
- fun organizationId(organizationId: JsonField) = apply {
- this.organizationId = organizationId
- }
-
- /** Source identifier for the context */
- fun source(source: String) = source(JsonField.of(source))
-
- /**
- * Sets [Builder.source] to an arbitrary JSON value.
- *
- * You should usually call [Builder.source] with a well-typed [String] value instead.
- * This method is primarily for setting the field to an undocumented or not yet
- * supported value.
- */
- fun source(source: JsonField) = apply { this.source = source }
-
/** Optional user ID */
+ @Deprecated("deprecated")
fun userId(userId: String?) = userId(JsonField.ofNullable(userId))
/** Alias for calling [Builder.userId] with `userId.orElse(null)`. */
+ @Deprecated("deprecated")
fun userId(userId: Optional) = userId(userId.getOrNull())
/**
@@ -595,6 +619,7 @@ private constructor(
* This method is primarily for setting the field to an undocumented or not yet
* supported value.
*/
+ @Deprecated("deprecated")
fun userId(userId: JsonField) = apply { this.userId = userId }
fun additionalProperties(additionalProperties: Map) = apply {
@@ -620,13 +645,21 @@ private constructor(
* Returns an immutable instance of [Body].
*
* Further updates to this [Builder] will not mutate the returned instance.
+ *
+ * The following fields are required:
+ * ```java
+ * .organizationId()
+ * .source()
+ * ```
+ *
+ * @throws IllegalStateException if any required field is unset.
*/
fun build(): Body =
Body(
+ checkRequired("organizationId", organizationId),
+ checkRequired("source", source),
byDoc,
byId,
- organizationId,
- source,
userId,
additionalProperties.toMutableMap(),
)
@@ -639,10 +672,10 @@ private constructor(
return@apply
}
- byDoc()
- byId()
organizationId()
source()
+ byDoc()
+ byId()
userId()
validated = true
}
@@ -663,10 +696,10 @@ private constructor(
*/
@JvmSynthetic
internal fun validity(): Int =
- (if (byDoc.asKnown().isPresent) 1 else 0) +
- (if (byId.asKnown().isPresent) 1 else 0) +
- (if (organizationId.asKnown().isPresent) 1 else 0) +
+ (if (organizationId.asKnown().isPresent) 1 else 0) +
(if (source.asKnown().isPresent) 1 else 0) +
+ (if (byDoc.asKnown().isPresent) 1 else 0) +
+ (if (byId.asKnown().isPresent) 1 else 0) +
(if (userId.asKnown().isPresent) 1 else 0)
override fun equals(other: Any?): Boolean {
@@ -675,22 +708,22 @@ private constructor(
}
return other is Body &&
- byDoc == other.byDoc &&
- byId == other.byId &&
organizationId == other.organizationId &&
source == other.source &&
+ byDoc == other.byDoc &&
+ byId == other.byId &&
userId == other.userId &&
additionalProperties == other.additionalProperties
}
private val hashCode: Int by lazy {
- Objects.hash(byDoc, byId, organizationId, source, userId, additionalProperties)
+ Objects.hash(organizationId, source, byDoc, byId, userId, additionalProperties)
}
override fun hashCode(): Int = hashCode
override fun toString() =
- "Body{byDoc=$byDoc, byId=$byId, organizationId=$organizationId, source=$source, userId=$userId, additionalProperties=$additionalProperties}"
+ "Body{organizationId=$organizationId, source=$source, byDoc=$byDoc, byId=$byId, userId=$userId, additionalProperties=$additionalProperties}"
}
override fun equals(other: Any?): Boolean {
diff --git a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextSearchParams.kt b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextSearchParams.kt
index 3f885bf..8e57434 100644
--- a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextSearchParams.kt
+++ b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextSearchParams.kt
@@ -27,11 +27,28 @@ import kotlin.jvm.optionals.getOrNull
*/
class ContextSearchParams
private constructor(
+ private val metadata: Metadata?,
+ private val mode: Mode?,
private val body: Body,
private val additionalHeaders: Headers,
private val additionalQueryParams: QueryParams,
) : Params {
+ /**
+ * Controls whether metadata is included in the response:
+ * - metadata=true → metadata will be included in each context item in the response.
+ * - metadata=false (or omitted) → metadata will be excluded from the response for better
+ * performance.
+ */
+ fun metadata(): Optional = Optional.ofNullable(metadata)
+
+ /**
+ * Controls the search mode:
+ * - mode=fast → prioritizes speed over completeness.
+ * - mode=standard → performs a comprehensive search (default if omitted).
+ */
+ fun mode(): Optional = Optional.ofNullable(mode)
+
/**
* Minimum similarity threshold
*
@@ -56,8 +73,15 @@ private constructor(
*/
fun similarityThreshold(): Double = body.similarityThreshold()
- /** Additional metadata for the search */
- fun _metadata(): JsonValue = body._metadata()
+ /**
+ * Additional metadata for the search
+ *
+ * This arbitrary value can be deserialized into a custom type using the `convert` method:
+ * ```java
+ * MyClass myObject = contextSearchParams.bodyMetadata().convert(MyClass.class);
+ * ```
+ */
+ fun _bodyMetadata(): JsonValue = body._bodyMetadata()
/**
* Search scope
@@ -73,7 +97,7 @@ private constructor(
* @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if the
* server responded with an unexpected value).
*/
- fun userId(): Optional = body.userId()
+ @Deprecated("deprecated") fun userId(): Optional = body.userId()
/**
* Returns the raw JSON value of [minimumSimilarityThreshold].
@@ -110,7 +134,7 @@ private constructor(
*
* Unlike [userId], this method doesn't throw if the JSON field has an unexpected type.
*/
- fun _userId(): JsonField = body._userId()
+ @Deprecated("deprecated") fun _userId(): JsonField = body._userId()
fun _additionalBodyProperties(): Map = body._additionalProperties()
@@ -140,17 +164,42 @@ private constructor(
/** A builder for [ContextSearchParams]. */
class Builder internal constructor() {
+ private var metadata: Metadata? = null
+ private var mode: Mode? = null
private var body: Body.Builder = Body.builder()
private var additionalHeaders: Headers.Builder = Headers.builder()
private var additionalQueryParams: QueryParams.Builder = QueryParams.builder()
@JvmSynthetic
internal fun from(contextSearchParams: ContextSearchParams) = apply {
+ metadata = contextSearchParams.metadata
+ mode = contextSearchParams.mode
body = contextSearchParams.body.toBuilder()
additionalHeaders = contextSearchParams.additionalHeaders.toBuilder()
additionalQueryParams = contextSearchParams.additionalQueryParams.toBuilder()
}
+ /**
+ * Controls whether metadata is included in the response:
+ * - metadata=true → metadata will be included in each context item in the response.
+ * - metadata=false (or omitted) → metadata will be excluded from the response for better
+ * performance.
+ */
+ fun metadata(metadata: Metadata?) = apply { this.metadata = metadata }
+
+ /** Alias for calling [Builder.metadata] with `metadata.orElse(null)`. */
+ fun metadata(metadata: Optional) = metadata(metadata.getOrNull())
+
+ /**
+ * Controls the search mode:
+ * - mode=fast → prioritizes speed over completeness.
+ * - mode=standard → performs a comprehensive search (default if omitted).
+ */
+ fun mode(mode: Mode?) = apply { this.mode = mode }
+
+ /** Alias for calling [Builder.mode] with `mode.orElse(null)`. */
+ fun mode(mode: Optional) = mode(mode.getOrNull())
+
/**
* Sets the entire request body.
*
@@ -159,7 +208,7 @@ private constructor(
* - [minimumSimilarityThreshold]
* - [query]
* - [similarityThreshold]
- * - [metadata]
+ * - [bodyMetadata]
* - [scope]
* - etc.
*/
@@ -209,7 +258,7 @@ private constructor(
}
/** Additional metadata for the search */
- fun metadata(metadata: JsonValue) = apply { body.metadata(metadata) }
+ fun bodyMetadata(bodyMetadata: JsonValue) = apply { body.bodyMetadata(bodyMetadata) }
/** Search scope */
fun scope(scope: Scope) = apply { body.scope(scope) }
@@ -223,7 +272,7 @@ private constructor(
fun scope(scope: JsonField) = apply { body.scope(scope) }
/** The ID of the user making the request */
- fun userId(userId: String) = apply { body.userId(userId) }
+ @Deprecated("deprecated") fun userId(userId: String) = apply { body.userId(userId) }
/**
* Sets [Builder.userId] to an arbitrary JSON value.
@@ -231,6 +280,7 @@ private constructor(
* You should usually call [Builder.userId] with a well-typed [String] value instead. This
* method is primarily for setting the field to an undocumented or not yet supported value.
*/
+ @Deprecated("deprecated")
fun userId(userId: JsonField) = apply { body.userId(userId) }
fun additionalBodyProperties(additionalBodyProperties: Map) = apply {
@@ -366,6 +416,8 @@ private constructor(
*/
fun build(): ContextSearchParams =
ContextSearchParams(
+ metadata,
+ mode,
body.build(),
additionalHeaders.build(),
additionalQueryParams.build(),
@@ -376,7 +428,14 @@ private constructor(
override fun _headers(): Headers = additionalHeaders
- override fun _queryParams(): QueryParams = additionalQueryParams
+ override fun _queryParams(): QueryParams =
+ QueryParams.builder()
+ .apply {
+ metadata?.let { put("metadata", it.toString()) }
+ mode?.let { put("mode", it.toString()) }
+ putAll(additionalQueryParams)
+ }
+ .build()
class Body
@JsonCreator(mode = JsonCreator.Mode.DISABLED)
@@ -384,7 +443,7 @@ private constructor(
private val minimumSimilarityThreshold: JsonField,
private val query: JsonField,
private val similarityThreshold: JsonField,
- private val metadata: JsonValue,
+ private val bodyMetadata: JsonValue,
private val scope: JsonField,
private val userId: JsonField,
private val additionalProperties: MutableMap,
@@ -399,14 +458,16 @@ private constructor(
@JsonProperty("similarity_threshold")
@ExcludeMissing
similarityThreshold: JsonField = JsonMissing.of(),
- @JsonProperty("metadata") @ExcludeMissing metadata: JsonValue = JsonMissing.of(),
+ @JsonProperty("body_metadata")
+ @ExcludeMissing
+ bodyMetadata: JsonValue = JsonMissing.of(),
@JsonProperty("scope") @ExcludeMissing scope: JsonField = JsonMissing.of(),
@JsonProperty("user_id") @ExcludeMissing userId: JsonField = JsonMissing.of(),
) : this(
minimumSimilarityThreshold,
query,
similarityThreshold,
- metadata,
+ bodyMetadata,
scope,
userId,
mutableMapOf(),
@@ -437,8 +498,15 @@ private constructor(
*/
fun similarityThreshold(): Double = similarityThreshold.getRequired("similarity_threshold")
- /** Additional metadata for the search */
- @JsonProperty("metadata") @ExcludeMissing fun _metadata(): JsonValue = metadata
+ /**
+ * Additional metadata for the search
+ *
+ * This arbitrary value can be deserialized into a custom type using the `convert` method:
+ * ```java
+ * MyClass myObject = body.bodyMetadata().convert(MyClass.class);
+ * ```
+ */
+ @JsonProperty("body_metadata") @ExcludeMissing fun _bodyMetadata(): JsonValue = bodyMetadata
/**
* Search scope
@@ -454,7 +522,7 @@ private constructor(
* @throws AlchemystAiInvalidDataException if the JSON field has an unexpected type (e.g. if
* the server responded with an unexpected value).
*/
- fun userId(): Optional = userId.getOptional("user_id")
+ @Deprecated("deprecated") fun userId(): Optional = userId.getOptional("user_id")
/**
* Returns the raw JSON value of [minimumSimilarityThreshold].
@@ -495,7 +563,10 @@ private constructor(
*
* Unlike [userId], this method doesn't throw if the JSON field has an unexpected type.
*/
- @JsonProperty("user_id") @ExcludeMissing fun _userId(): JsonField = userId
+ @Deprecated("deprecated")
+ @JsonProperty("user_id")
+ @ExcludeMissing
+ fun _userId(): JsonField = userId
@JsonAnySetter
private fun putAdditionalProperty(key: String, value: JsonValue) {
@@ -530,7 +601,7 @@ private constructor(
private var minimumSimilarityThreshold: JsonField? = null
private var query: JsonField? = null
private var similarityThreshold: JsonField? = null
- private var metadata: JsonValue = JsonMissing.of()
+ private var bodyMetadata: JsonValue = JsonMissing.of()
private var scope: JsonField = JsonMissing.of()
private var userId: JsonField = JsonMissing.of()
private var additionalProperties: MutableMap = mutableMapOf()
@@ -540,7 +611,7 @@ private constructor(
minimumSimilarityThreshold = body.minimumSimilarityThreshold
query = body.query
similarityThreshold = body.similarityThreshold
- metadata = body.metadata
+ bodyMetadata = body.bodyMetadata
scope = body.scope
userId = body.userId
additionalProperties = body.additionalProperties.toMutableMap()
@@ -589,7 +660,7 @@ private constructor(
}
/** Additional metadata for the search */
- fun metadata(metadata: JsonValue) = apply { this.metadata = metadata }
+ fun bodyMetadata(bodyMetadata: JsonValue) = apply { this.bodyMetadata = bodyMetadata }
/** Search scope */
fun scope(scope: Scope) = scope(JsonField.of(scope))
@@ -604,7 +675,7 @@ private constructor(
fun scope(scope: JsonField) = apply { this.scope = scope }
/** The ID of the user making the request */
- fun userId(userId: String) = userId(JsonField.of(userId))
+ @Deprecated("deprecated") fun userId(userId: String) = userId(JsonField.of(userId))
/**
* Sets [Builder.userId] to an arbitrary JSON value.
@@ -613,6 +684,7 @@ private constructor(
* This method is primarily for setting the field to an undocumented or not yet
* supported value.
*/
+ @Deprecated("deprecated")
fun userId(userId: JsonField) = apply { this.userId = userId }
fun additionalProperties(additionalProperties: Map) = apply {
@@ -653,7 +725,7 @@ private constructor(
checkRequired("minimumSimilarityThreshold", minimumSimilarityThreshold),
checkRequired("query", query),
checkRequired("similarityThreshold", similarityThreshold),
- metadata,
+ bodyMetadata,
scope,
userId,
additionalProperties.toMutableMap(),
@@ -706,7 +778,7 @@ private constructor(
minimumSimilarityThreshold == other.minimumSimilarityThreshold &&
query == other.query &&
similarityThreshold == other.similarityThreshold &&
- metadata == other.metadata &&
+ bodyMetadata == other.bodyMetadata &&
scope == other.scope &&
userId == other.userId &&
additionalProperties == other.additionalProperties
@@ -717,7 +789,7 @@ private constructor(
minimumSimilarityThreshold,
query,
similarityThreshold,
- metadata,
+ bodyMetadata,
scope,
userId,
additionalProperties,
@@ -727,7 +799,7 @@ private constructor(
override fun hashCode(): Int = hashCode
override fun toString() =
- "Body{minimumSimilarityThreshold=$minimumSimilarityThreshold, query=$query, similarityThreshold=$similarityThreshold, metadata=$metadata, scope=$scope, userId=$userId, additionalProperties=$additionalProperties}"
+ "Body{minimumSimilarityThreshold=$minimumSimilarityThreshold, query=$query, similarityThreshold=$similarityThreshold, bodyMetadata=$bodyMetadata, scope=$scope, userId=$userId, additionalProperties=$additionalProperties}"
}
/** Search scope */
@@ -858,19 +930,287 @@ private constructor(
override fun toString() = value.toString()
}
+ /**
+ * Controls whether metadata is included in the response:
+ * - metadata=true → metadata will be included in each context item in the response.
+ * - metadata=false (or omitted) → metadata will be excluded from the response for better
+ * performance.
+ */
+ class Metadata @JsonCreator private constructor(private val value: JsonField) : Enum {
+
+ /**
+ * Returns this class instance's raw value.
+ *
+ * This is usually only useful if this instance was deserialized from data that doesn't
+ * match any known member, and you want to know that value. For example, if the SDK is on an
+ * older version than the API, then the API may respond with new members that the SDK is
+ * unaware of.
+ */
+ @com.fasterxml.jackson.annotation.JsonValue fun _value(): JsonField = value
+
+ companion object {
+
+ @JvmField val TRUE = of("true")
+
+ @JvmField val FALSE = of("false")
+
+ @JvmStatic fun of(value: String) = Metadata(JsonField.of(value))
+ }
+
+ /** An enum containing [Metadata]'s known values. */
+ enum class Known {
+ TRUE,
+ FALSE,
+ }
+
+ /**
+ * An enum containing [Metadata]'s known values, as well as an [_UNKNOWN] member.
+ *
+ * An instance of [Metadata] can contain an unknown value in a couple of cases:
+ * - It was deserialized from data that doesn't match any known member. For example, if the
+ * SDK is on an older version than the API, then the API may respond with new members that
+ * the SDK is unaware of.
+ * - It was constructed with an arbitrary value using the [of] method.
+ */
+ enum class Value {
+ TRUE,
+ FALSE,
+ /** An enum member indicating that [Metadata] was instantiated with an unknown value. */
+ _UNKNOWN,
+ }
+
+ /**
+ * Returns an enum member corresponding to this class instance's value, or [Value._UNKNOWN]
+ * if the class was instantiated with an unknown value.
+ *
+ * Use the [known] method instead if you're certain the value is always known or if you want
+ * to throw for the unknown case.
+ */
+ fun value(): Value =
+ when (this) {
+ TRUE -> Value.TRUE
+ FALSE -> Value.FALSE
+ else -> Value._UNKNOWN
+ }
+
+ /**
+ * Returns an enum member corresponding to this class instance's value.
+ *
+ * Use the [value] method instead if you're uncertain the value is always known and don't
+ * want to throw for the unknown case.
+ *
+ * @throws AlchemystAiInvalidDataException if this class instance's value is a not a known
+ * member.
+ */
+ fun known(): Known =
+ when (this) {
+ TRUE -> Known.TRUE
+ FALSE -> Known.FALSE
+ else -> throw AlchemystAiInvalidDataException("Unknown Metadata: $value")
+ }
+
+ /**
+ * Returns this class instance's primitive wire representation.
+ *
+ * This differs from the [toString] method because that method is primarily for debugging
+ * and generally doesn't throw.
+ *
+ * @throws AlchemystAiInvalidDataException if this class instance's value does not have the
+ * expected primitive type.
+ */
+ fun asString(): String =
+ _value().asString().orElseThrow {
+ AlchemystAiInvalidDataException("Value is not a String")
+ }
+
+ private var validated: Boolean = false
+
+ fun validate(): Metadata = apply {
+ if (validated) {
+ return@apply
+ }
+
+ known()
+ validated = true
+ }
+
+ fun isValid(): Boolean =
+ try {
+ validate()
+ true
+ } catch (e: AlchemystAiInvalidDataException) {
+ false
+ }
+
+ /**
+ * Returns a score indicating how many valid values are contained in this object
+ * recursively.
+ *
+ * Used for best match union deserialization.
+ */
+ @JvmSynthetic internal fun validity(): Int = if (value() == Value._UNKNOWN) 0 else 1
+
+ override fun equals(other: Any?): Boolean {
+ if (this === other) {
+ return true
+ }
+
+ return other is Metadata && value == other.value
+ }
+
+ override fun hashCode() = value.hashCode()
+
+ override fun toString() = value.toString()
+ }
+
+ /**
+ * Controls the search mode:
+ * - mode=fast → prioritizes speed over completeness.
+ * - mode=standard → performs a comprehensive search (default if omitted).
+ */
+ class Mode @JsonCreator private constructor(private val value: JsonField) : Enum {
+
+ /**
+ * Returns this class instance's raw value.
+ *
+ * This is usually only useful if this instance was deserialized from data that doesn't
+ * match any known member, and you want to know that value. For example, if the SDK is on an
+ * older version than the API, then the API may respond with new members that the SDK is
+ * unaware of.
+ */
+ @com.fasterxml.jackson.annotation.JsonValue fun _value(): JsonField = value
+
+ companion object {
+
+ @JvmField val FAST = of("fast")
+
+ @JvmField val STANDARD = of("standard")
+
+ @JvmStatic fun of(value: String) = Mode(JsonField.of(value))
+ }
+
+ /** An enum containing [Mode]'s known values. */
+ enum class Known {
+ FAST,
+ STANDARD,
+ }
+
+ /**
+ * An enum containing [Mode]'s known values, as well as an [_UNKNOWN] member.
+ *
+ * An instance of [Mode] can contain an unknown value in a couple of cases:
+ * - It was deserialized from data that doesn't match any known member. For example, if the
+ * SDK is on an older version than the API, then the API may respond with new members that
+ * the SDK is unaware of.
+ * - It was constructed with an arbitrary value using the [of] method.
+ */
+ enum class Value {
+ FAST,
+ STANDARD,
+ /** An enum member indicating that [Mode] was instantiated with an unknown value. */
+ _UNKNOWN,
+ }
+
+ /**
+ * Returns an enum member corresponding to this class instance's value, or [Value._UNKNOWN]
+ * if the class was instantiated with an unknown value.
+ *
+ * Use the [known] method instead if you're certain the value is always known or if you want
+ * to throw for the unknown case.
+ */
+ fun value(): Value =
+ when (this) {
+ FAST -> Value.FAST
+ STANDARD -> Value.STANDARD
+ else -> Value._UNKNOWN
+ }
+
+ /**
+ * Returns an enum member corresponding to this class instance's value.
+ *
+ * Use the [value] method instead if you're uncertain the value is always known and don't
+ * want to throw for the unknown case.
+ *
+ * @throws AlchemystAiInvalidDataException if this class instance's value is a not a known
+ * member.
+ */
+ fun known(): Known =
+ when (this) {
+ FAST -> Known.FAST
+ STANDARD -> Known.STANDARD
+ else -> throw AlchemystAiInvalidDataException("Unknown Mode: $value")
+ }
+
+ /**
+ * Returns this class instance's primitive wire representation.
+ *
+ * This differs from the [toString] method because that method is primarily for debugging
+ * and generally doesn't throw.
+ *
+ * @throws AlchemystAiInvalidDataException if this class instance's value does not have the
+ * expected primitive type.
+ */
+ fun asString(): String =
+ _value().asString().orElseThrow {
+ AlchemystAiInvalidDataException("Value is not a String")
+ }
+
+ private var validated: Boolean = false
+
+ fun validate(): Mode = apply {
+ if (validated) {
+ return@apply
+ }
+
+ known()
+ validated = true
+ }
+
+ fun isValid(): Boolean =
+ try {
+ validate()
+ true
+ } catch (e: AlchemystAiInvalidDataException) {
+ false
+ }
+
+ /**
+ * Returns a score indicating how many valid values are contained in this object
+ * recursively.
+ *
+ * Used for best match union deserialization.
+ */
+ @JvmSynthetic internal fun validity(): Int = if (value() == Value._UNKNOWN) 0 else 1
+
+ override fun equals(other: Any?): Boolean {
+ if (this === other) {
+ return true
+ }
+
+ return other is Mode && value == other.value
+ }
+
+ override fun hashCode() = value.hashCode()
+
+ override fun toString() = value.toString()
+ }
+
override fun equals(other: Any?): Boolean {
if (this === other) {
return true
}
return other is ContextSearchParams &&
+ metadata == other.metadata &&
+ mode == other.mode &&
body == other.body &&
additionalHeaders == other.additionalHeaders &&
additionalQueryParams == other.additionalQueryParams
}
- override fun hashCode(): Int = Objects.hash(body, additionalHeaders, additionalQueryParams)
+ override fun hashCode(): Int =
+ Objects.hash(metadata, mode, body, additionalHeaders, additionalQueryParams)
override fun toString() =
- "ContextSearchParams{body=$body, additionalHeaders=$additionalHeaders, additionalQueryParams=$additionalQueryParams}"
+ "ContextSearchParams{metadata=$metadata, mode=$mode, body=$body, additionalHeaders=$additionalHeaders, additionalQueryParams=$additionalQueryParams}"
}
diff --git a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextSearchResponse.kt b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextSearchResponse.kt
index f44c895..f502ff2 100644
--- a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextSearchResponse.kt
+++ b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/ContextSearchResponse.kt
@@ -196,6 +196,14 @@ private constructor(
*/
fun createdAt(): Optional = createdAt.getOptional("createdAt")
+ /**
+ * Only included when query parameter metadata=true
+ *
+ * This arbitrary value can be deserialized into a custom type using the `convert` method:
+ * ```java
+ * MyClass myObject = context.metadata().convert(MyClass.class);
+ * ```
+ */
@JsonProperty("metadata") @ExcludeMissing fun _metadata(): JsonValue = metadata
/**
@@ -304,6 +312,7 @@ private constructor(
this.createdAt = createdAt
}
+ /** Only included when query parameter metadata=true */
fun metadata(metadata: JsonValue) = apply { this.metadata = metadata }
fun score(score: Double) = score(JsonField.of(score))
diff --git a/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/addasync/AddAsyncCancelParams.kt b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/addasync/AddAsyncCancelParams.kt
new file mode 100644
index 0000000..b6b5034
--- /dev/null
+++ b/alchemyst-ai-java-core/src/main/kotlin/com/alchemystai/sdk/models/v1/context/addasync/AddAsyncCancelParams.kt
@@ -0,0 +1,234 @@
+// File generated from our OpenAPI spec by Stainless.
+
+package com.alchemystai.sdk.models.v1.context.addasync
+
+import com.alchemystai.sdk.core.JsonValue
+import com.alchemystai.sdk.core.Params
+import com.alchemystai.sdk.core.http.Headers
+import com.alchemystai.sdk.core.http.QueryParams
+import com.alchemystai.sdk.core.toImmutable
+import java.util.Objects
+import java.util.Optional
+import kotlin.jvm.optionals.getOrNull
+
+/**
+ * Attempts to cancel a context add job by job id.
+ * - If the job is already completed or failed, returns 404.
+ * - If the job is currently running ("active"), returns 409 and cannot be cancelled.
+ * - Only jobs in "waiting" or "delayed" state can be cancelled.
+ */
+class AddAsyncCancelParams
+private constructor(
+ private val id: String?,
+ private val additionalHeaders: Headers,
+ private val additionalQueryParams: QueryParams,
+ private val additionalBodyProperties: Map,
+) : Params {
+
+ fun id(): Optional = Optional.ofNullable(id)
+
+ /** Additional body properties to send with the request. */
+ fun _additionalBodyProperties(): Map = additionalBodyProperties
+
+ /** Additional headers to send with the request. */
+ fun _additionalHeaders(): Headers = additionalHeaders
+
+ /** Additional query param to send with the request. */
+ fun _additionalQueryParams(): QueryParams = additionalQueryParams
+
+ fun toBuilder() = Builder().from(this)
+
+ companion object {
+
+ @JvmStatic fun none(): AddAsyncCancelParams = builder().build()
+
+ /** Returns a mutable builder for constructing an instance of [AddAsyncCancelParams]. */
+ @JvmStatic fun builder() = Builder()
+ }
+
+ /** A builder for [AddAsyncCancelParams]. */
+ class Builder internal constructor() {
+
+ private var id: String? = null
+ private var additionalHeaders: Headers.Builder = Headers.builder()
+ private var additionalQueryParams: QueryParams.Builder = QueryParams.builder()
+ private var additionalBodyProperties: MutableMap = mutableMapOf()
+
+ @JvmSynthetic
+ internal fun from(addAsyncCancelParams: AddAsyncCancelParams) = apply {
+ id = addAsyncCancelParams.id
+ additionalHeaders = addAsyncCancelParams.additionalHeaders.toBuilder()
+ additionalQueryParams = addAsyncCancelParams.additionalQueryParams.toBuilder()
+ additionalBodyProperties = addAsyncCancelParams.additionalBodyProperties.toMutableMap()
+ }
+
+ fun id(id: String?) = apply { this.id = id }
+
+ /** Alias for calling [Builder.id] with `id.orElse(null)`. */
+ fun id(id: Optional) = id(id.getOrNull())
+
+ fun additionalHeaders(additionalHeaders: Headers) = apply {
+ this.additionalHeaders.clear()
+ putAllAdditionalHeaders(additionalHeaders)
+ }
+
+ fun additionalHeaders(additionalHeaders: Map>) = apply {
+ this.additionalHeaders.clear()
+ putAllAdditionalHeaders(additionalHeaders)
+ }
+
+ fun putAdditionalHeader(name: String, value: String) = apply {
+ additionalHeaders.put(name, value)
+ }
+
+ fun putAdditionalHeaders(name: String, values: Iterable) = apply {
+ additionalHeaders.put(name, values)
+ }
+
+ fun putAllAdditionalHeaders(additionalHeaders: Headers) = apply {
+ this.additionalHeaders.putAll(additionalHeaders)
+ }
+
+ fun putAllAdditionalHeaders(additionalHeaders: Map>) = apply {
+ this.additionalHeaders.putAll(additionalHeaders)
+ }
+
+ fun replaceAdditionalHeaders(name: String, value: String) = apply {
+ additionalHeaders.replace(name, value)
+ }
+
+ fun replaceAdditionalHeaders(name: String, values: Iterable) = apply {
+ additionalHeaders.replace(name, values)
+ }
+
+ fun replaceAllAdditionalHeaders(additionalHeaders: Headers) = apply {
+ this.additionalHeaders.replaceAll(additionalHeaders)
+ }
+
+ fun replaceAllAdditionalHeaders(additionalHeaders: Map>) = apply {
+ this.additionalHeaders.replaceAll(additionalHeaders)
+ }
+
+ fun removeAdditionalHeaders(name: String) = apply { additionalHeaders.remove(name) }
+
+ fun removeAllAdditionalHeaders(names: Set) = apply {
+ additionalHeaders.removeAll(names)
+ }
+
+ fun additionalQueryParams(additionalQueryParams: QueryParams) = apply {
+ this.additionalQueryParams.clear()
+ putAllAdditionalQueryParams(additionalQueryParams)
+ }
+
+ fun additionalQueryParams(additionalQueryParams: Map>) = apply {
+ this.additionalQueryParams.clear()
+ putAllAdditionalQueryParams(additionalQueryParams)
+ }
+
+ fun putAdditionalQueryParam(key: String, value: String) = apply {
+ additionalQueryParams.put(key, value)
+ }
+
+ fun putAdditionalQueryParams(key: String, values: Iterable) = apply {
+ additionalQueryParams.put(key, values)
+ }
+
+ fun putAllAdditionalQueryParams(additionalQueryParams: QueryParams) = apply {
+ this.additionalQueryParams.putAll(additionalQueryParams)
+ }
+
+ fun putAllAdditionalQueryParams(additionalQueryParams: Map>) =
+ apply {
+ this.additionalQueryParams.putAll(additionalQueryParams)
+ }
+
+ fun replaceAdditionalQueryParams(key: String, value: String) = apply {
+ additionalQueryParams.replace(key, value)
+ }
+
+ fun replaceAdditionalQueryParams(key: String, values: Iterable) = apply {
+ additionalQueryParams.replace(key, values)
+ }
+
+ fun replaceAllAdditionalQueryParams(additionalQueryParams: QueryParams) = apply {
+ this.additionalQueryParams.replaceAll(additionalQueryParams)
+ }
+
+ fun replaceAllAdditionalQueryParams(additionalQueryParams: Map>) =
+ apply {
+ this.additionalQueryParams.replaceAll(additionalQueryParams)
+ }
+
+ fun removeAdditionalQueryParams(key: String) = apply { additionalQueryParams.remove(key) }
+
+ fun removeAllAdditionalQueryParams(keys: Set) = apply {
+ additionalQueryParams.removeAll(keys)
+ }
+
+ fun additionalBodyProperties(additionalBodyProperties: Map) = apply {
+ this.additionalBodyProperties.clear()
+ putAllAdditionalBodyProperties(additionalBodyProperties)
+ }
+
+ fun putAdditionalBodyProperty(key: String, value: JsonValue) = apply {
+ additionalBodyProperties.put(key, value)
+ }
+
+ fun putAllAdditionalBodyProperties(additionalBodyProperties: Map) =
+ apply {
+ this.additionalBodyProperties.putAll(additionalBodyProperties)
+ }
+
+ fun removeAdditionalBodyProperty(key: String) = apply {
+ additionalBodyProperties.remove(key)
+ }
+
+ fun removeAllAdditionalBodyProperties(keys: Set) = apply {
+ keys.forEach(::removeAdditionalBodyProperty)
+ }
+
+ /**
+ * Returns an immutable instance of [AddAsyncCancelParams].
+ *
+ * Further updates to this [Builder] will not mutate the returned instance.
+ */
+ fun build(): AddAsyncCancelParams =
+ AddAsyncCancelParams(
+ id,
+ additionalHeaders.build(),
+ additionalQueryParams.build(),
+ additionalBodyProperties.toImmutable(),
+ )
+ }
+
+ fun _body(): Optional