diff --git a/.github/workflows/create-releases.yml b/.github/workflows/create-releases.yml index 23cf4386..2b0de813 100644 --- a/.github/workflows/create-releases.yml +++ b/.github/workflows/create-releases.yml @@ -40,6 +40,5 @@ jobs: ${{ github.workspace }}/artifacts/packages/*.nupkg --source https://api.nuget.org/v3/index.json --api-key $NUGET_API_KEY - --skip-duplicate env: NUGET_API_KEY: ${{ secrets.ANTHROPIC_NUGET_API_KEY || secrets.NUGET_API_KEY }} diff --git a/.github/workflows/publish-nuget.yml b/.github/workflows/publish-nuget.yml index 1ea1d60f..3fd89c2d 100644 --- a/.github/workflows/publish-nuget.yml +++ b/.github/workflows/publish-nuget.yml @@ -27,6 +27,5 @@ jobs: ${{ github.workspace }}/artifacts/packages/*.nupkg --source https://api.nuget.org/v3/index.json --api-key $NUGET_API_KEY - --skip-duplicate env: NUGET_API_KEY: ${{ secrets.ANTHROPIC_NUGET_API_KEY || secrets.NUGET_API_KEY }} \ No newline at end of file diff --git a/.release-please-manifest.json b/.release-please-manifest.json index 74705098..f03113bb 100644 --- a/.release-please-manifest.json +++ b/.release-please-manifest.json @@ -1,4 +1,4 @@ { - ".": "11.0.0", - "src/Anthropic.Foundry": "0.1.0" -} \ No newline at end of file + "src/Anthropic": "12.0.0", + "src/Anthropic.Foundry": "0.2.0" +} diff --git a/.stats.yml b/.stats.yml index e008716e..bd79f46f 100644 --- a/.stats.yml +++ b/.stats.yml @@ -1,4 +1,4 @@ configured_endpoints: 32 openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/anthropic%2Fanthropic-a49e89deec4e00d1da490808099d66e2001531b12d8666a7f5d0b496f760440d.yml openapi_spec_hash: c93ef3808c58e233b01966ff154f31ce -config_hash: 0abc2a1f94e35774a88fceb60e703c5f +config_hash: a5d8cd02f9a686d4e0baa7ba652e3e55 diff --git a/CHANGELOG.md b/CHANGELOG.md index f0245589..c63f98ba 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,4 @@ +<<<<<<< HEAD # Changelog ## 11.0.0 (2025-12-01) @@ -347,3 +348,312 @@ Full Changelog: [v0.0.1...v0.1.0](https://github.com/anthropics/anthropic-sdk-cs * **client:** refine enum representation ([a3e973b](https://github.com/anthropics/anthropic-sdk-csharp/commit/a3e973b0e6d057e58e6f0bd08c8a5635da896974)) * **client:** use plural for service namespace ([843da53](https://github.com/anthropics/anthropic-sdk-csharp/commit/843da53c91a4e925298aae8907f8990b7e13de9e)) +||||||| cbf1ebb7 +======= +# Changelog + +## 10.4.0 (2025-11-25) + +Full Changelog: [v10.3.0...v10.4.0](https://github.com/anthropics/anthropic-sdk-csharp/compare/v10.3.0...v10.4.0) + +### Features + +* **client:** support .NET Standard 2.0 ([70928cd](https://github.com/anthropics/anthropic-sdk-csharp/commit/70928cdd02452b2b7ad37f419b43d92680e02f9d)) + + +### Bug Fixes + +* **internal:** don't format csproj files ([76affbf](https://github.com/anthropics/anthropic-sdk-csharp/commit/76affbf85b3f9c04bd500020644660265d361fb6)) + + +### Chores + +* **internal:** add logo to nuget package ([#181](https://github.com/anthropics/anthropic-sdk-csharp/issues/181)) ([f2ca130](https://github.com/anthropics/anthropic-sdk-csharp/commit/f2ca130ab65ec6db6ce164a33a7a820de5187e1a)) +* **internal:** remove redundant keyword ([f33f185](https://github.com/anthropics/anthropic-sdk-csharp/commit/f33f185da453cc9c8293891cb653964d085e362e)) +* remove .keep ([#37](https://github.com/anthropics/anthropic-sdk-csharp/issues/37)) ([3974964](https://github.com/anthropics/anthropic-sdk-csharp/commit/3974964dbf738d0a265f77482e3c9fecefdc5f67)) + + +### Refactors + +* **internal:** remove abstract static methods ([3a3dffe](https://github.com/anthropics/anthropic-sdk-csharp/commit/3a3dffedbc11260c1b5e65606671f9898af9531b)) + +## 10.3.0 (2025-11-24) + +Full Changelog: [v10.2.1...v10.3.0](https://github.com/anthropics/anthropic-sdk-csharp/compare/v10.2.1...v10.3.0) + +### Features + +* **api:** adds support for Claude Opus 4.5, Effort, Advance Tool Use Features, Autocompaction, and Computer Use v5 ([144a820](https://github.com/anthropics/anthropic-sdk-csharp/commit/144a8209e522f5bba2174b1efd3d5607a2d7c145)) + + +### Bug Fixes + +* **internal:** install csharpier during ci lint phase ([8898df9](https://github.com/anthropics/anthropic-sdk-csharp/commit/8898df9bf709867ddf3851bd5f5c0acbd8d90764)) +* **internal:** minor project fixes ([3c344e2](https://github.com/anthropics/anthropic-sdk-csharp/commit/3c344e2db929ed43cc49854c791ea10e5e42489c)) +* **internal:** remove release notes from foundry readme ([afeaa2f](https://github.com/anthropics/anthropic-sdk-csharp/commit/afeaa2f526c3818c244bb351b4dad56a59883395)) + + +### Chores + +* **client:** change name of underlying properties for models and params ([75a2cce](https://github.com/anthropics/anthropic-sdk-csharp/commit/75a2ccecefaf3fff5a07138a3c38ff0b9b9df476)) +* formatting ([6850900](https://github.com/anthropics/anthropic-sdk-csharp/commit/6850900ae2b8f5da55381988af5d4cb5b2ee4351)) +* **internal:** update release please config ([980d7fd](https://github.com/anthropics/anthropic-sdk-csharp/commit/980d7fd21375f9125c0bd0f58a378a081bfa11bb)) + +## 10.2.1 (2025-11-20) + +Full Changelog: [v10.2.0...v10.2.1](https://github.com/anthropics/anthropic-sdk-csharp/compare/v10.2.0...v10.2.1) + +## 10.2.0 (2025-11-20) + +Full Changelog: [v10.1.2...v10.2.0](https://github.com/anthropics/anthropic-sdk-csharp/compare/v10.1.2...v10.2.0) + +### Features + +* **client:** additional methods for positional params ([8bc6323](https://github.com/anthropics/anthropic-sdk-csharp/commit/8bc6323c38ce551f995bec5e4b1584460b7f037b)) + + +### Bug Fixes + +* **client:** return correct type for foundry#WithOptions ([#18](https://github.com/anthropics/anthropic-sdk-csharp/issues/18)) ([f814a46](https://github.com/anthropics/anthropic-sdk-csharp/commit/f814a460503abf7fdf7a824b5bf446ef74d60f28)) +* use correct versions ([c78c8db](https://github.com/anthropics/anthropic-sdk-csharp/commit/c78c8db4b6effa6b1438bb879bcafdad2d155808)) + + +### Refactors + +* **client:** make unknown variants implicit ([eb0e5b6](https://github.com/anthropics/anthropic-sdk-csharp/commit/eb0e5b628d7090adc34300775043ecd26ccfffaf)) + +## 10.1.2 (2025-11-18) + +Full Changelog: [v10.1.1...v10.1.2](https://github.com/anthropics/anthropic-sdk-csharp/compare/v10.1.1...v10.1.2) + +### Bug Fixes + +* use correct version ([a808311](https://github.com/anthropics/anthropic-sdk-csharp/commit/a8083119584c82ec26e1d74f980b6c021e1fbb10)) + +## 10.1.1 (2025-11-18) + +Full Changelog: [v10.1.0...v10.1.1](https://github.com/anthropics/anthropic-sdk-csharp/compare/v10.1.0...v10.1.1) + +## 10.1.0 (2025-11-18) + +Full Changelog: [v10.0.1...v10.1.0](https://github.com/anthropics/anthropic-sdk-csharp/compare/v10.0.1...v10.1.0) + +### Features + +* add Foundry client ([8ddea23](https://github.com/anthropics/anthropic-sdk-csharp/commit/8ddea2363a799b366740779703f074fbe8dadf56)) + +## 10.0.1 (2025-11-18) + +Full Changelog: [v0.2.0...v10.0.1](https://github.com/anthropics/anthropic-sdk-csharp/compare/v0.2.0...v10.0.1) + +### ⚠ BREAKING CHANGES + +* **client:** improve names of some types +* **client:** use `DateTimeOffset` instead of `DateTime` +* **client:** flatten service namespaces +* **client:** interpret null as omitted in some properties + +### Features + +* **api:** add file download method ([a03d526](https://github.com/anthropics/anthropic-sdk-csharp/commit/a03d5267282ba893e96ca96c70c7b28326076d1a)) +* **api:** add support for structured outputs beta ([17ea9b3](https://github.com/anthropics/anthropic-sdk-csharp/commit/17ea9b388f10cfe621af9aeb9f3ddd799027fc09)) +* **api:** rename C# package to Anthropic ([2ba3485](https://github.com/anthropics/anthropic-sdk-csharp/commit/2ba34850dcd783b672aff1371970db7e5f0abc14)) +* **client:** add `HttpResponse.ReadAsStream` method ([677857b](https://github.com/anthropics/anthropic-sdk-csharp/commit/677857b53e4bcfbc3f6a7b0d3cd7e2c9af86c9cd)) +* **client:** add cancellation token support ([bf4c0e5](https://github.com/anthropics/anthropic-sdk-csharp/commit/bf4c0e57952376844c27f63311e70cb903c5897c)) +* **client:** add per-resource headers ([1d7658a](https://github.com/anthropics/anthropic-sdk-csharp/commit/1d7658ad37ade9ed4d5a73521f72cb3a389535de)) +* **client:** add retries support ([3327c9b](https://github.com/anthropics/anthropic-sdk-csharp/commit/3327c9b2fd704a2807a9d4453d1c99c7f12e97f9)) +* **client:** add some implicit operators ([bf26da8](https://github.com/anthropics/anthropic-sdk-csharp/commit/bf26da89cad05f586a7f24fbcf0ad5adcfefc44f)) +* **client:** send `User-Agent` header ([e8a0844](https://github.com/anthropics/anthropic-sdk-csharp/commit/e8a08449899460d22522336714d86264755e1a57)) +* **client:** send `X-Stainless-Arch` header ([d66d180](https://github.com/anthropics/anthropic-sdk-csharp/commit/d66d180ff7c04aff7ec53cfefaa1dff0236ce53c)) +* **client:** send `X-Stainless-Lang` and `X-Stainless-OS` headers ([bcc30e9](https://github.com/anthropics/anthropic-sdk-csharp/commit/bcc30e9a754798c96d28516d556e40c4e8cbf802)) +* **client:** send `X-Stainless-Package-Version` headers ([84bf583](https://github.com/anthropics/anthropic-sdk-csharp/commit/84bf583218f56682972add2c77784c88700eff53)) +* **client:** send `X-Stainless-Runtime` and `X-Stainless-Runtime-Version` ([94d2581](https://github.com/anthropics/anthropic-sdk-csharp/commit/94d25812e111657e81e9f7c27dfdab97c0af82f4)) +* **client:** send `X-Stainless-Timeout` header ([95ec578](https://github.com/anthropics/anthropic-sdk-csharp/commit/95ec578685f65b8ff008b35b4cf43f289107dc86)) +* **client:** validate constant values ([493a9ef](https://github.com/anthropics/anthropic-sdk-csharp/commit/493a9efb26479cf26e21d7c7c95b70507c0d3dc9)) +* **csharp:** enable nuget publishing ([4a4a1bc](https://github.com/anthropics/anthropic-sdk-csharp/commit/4a4a1bccd369b7f7b38db636c2f5846c43b7d826)) +* **docs:** add package/version notice ([76b74eb](https://github.com/anthropics/anthropic-sdk-csharp/commit/76b74eb7f1aaee9ba6cb1844b061aee8c1288633)) +* **docs:** Semver warning ([55c20ba](https://github.com/anthropics/anthropic-sdk-csharp/commit/55c20bad38b05b7a2ec166ca403214833103b9c1)) +* **docs:** tweak readme notice ([82d5990](https://github.com/anthropics/anthropic-sdk-csharp/commit/82d5990cb33ba6acc55d12954c94aafaa75b7f7d)) +* **docs:** Update README for nuget (instead of just github) ([6bde0b4](https://github.com/anthropics/anthropic-sdk-csharp/commit/6bde0b45452e1ecde305ebace0b8a063ac205e40)) +* **docs:** Update version refs in README ([70d787d](https://github.com/anthropics/anthropic-sdk-csharp/commit/70d787dcc7d47a79e47814209f81a1366a3460c7)) + + +### Bug Fixes + +* **client:** interpret null as omitted in some properties ([56059db](https://github.com/anthropics/anthropic-sdk-csharp/commit/56059db7047e7263cbd666f19293985577f8339d)) +* **client:** use `DateTimeOffset` instead of `DateTime` ([dbc7f6f](https://github.com/anthropics/anthropic-sdk-csharp/commit/dbc7f6f086dd0a75d869c1c683fa3c245c18f548)) +* use correct header name ([f6d0942](https://github.com/anthropics/anthropic-sdk-csharp/commit/f6d0942657fd87bc7b479602e1e913f404da0bb7)) + + +### Performance Improvements + +* **client:** optimize header creation ([3d37bb5](https://github.com/anthropics/anthropic-sdk-csharp/commit/3d37bb54241981dfbfdfc7a8f69c2430de808bfb)) + + +### Chores + +* **client:** deprecate some symbols ([b3446f6](https://github.com/anthropics/anthropic-sdk-csharp/commit/b3446f6d62f8d6e53a6871aee5979903f6b04498)) +* **internal:** add prism log file to gitignore ([8588901](https://github.com/anthropics/anthropic-sdk-csharp/commit/8588901ed4a32880165b344246bc3b8c1dc2464d)) +* **internal:** codegen related update ([cf3f5d5](https://github.com/anthropics/anthropic-sdk-csharp/commit/cf3f5d5f9af0f066c53c2dcb0d27bed5f602edce)) +* **internal:** delete empty test files ([a79abd1](https://github.com/anthropics/anthropic-sdk-csharp/commit/a79abd17f32d1313f77365faf0fed8d004ff48c3)) +* **internal:** improve devcontainer ([ab246ff](https://github.com/anthropics/anthropic-sdk-csharp/commit/ab246ffcde051808c017d73c46d18a769ec7d2c0)) +* **internal:** minor improvements to csproj and gitignore ([bf94b8c](https://github.com/anthropics/anthropic-sdk-csharp/commit/bf94b8c15a7f296780660134ceb251e28ee0ed23)) +* **internal:** reduce import qualification ([137c8b4](https://github.com/anthropics/anthropic-sdk-csharp/commit/137c8b4b2103d5b510698629359e7ef2a28512ad)) +* **internal:** update release please config ([bd94183](https://github.com/anthropics/anthropic-sdk-csharp/commit/bd9418322fe76a3c7db57375ddb2f0ba8ee49543)) + + +### Documentation + +* **client:** document max retries ([e1f611f](https://github.com/anthropics/anthropic-sdk-csharp/commit/e1f611fdd28e19788f0fe843396707d20bb069fa)) +* **client:** separate comment content into paragraphs ([1f89605](https://github.com/anthropics/anthropic-sdk-csharp/commit/1f89605692d5cfee120c740098f0a35ccded6d93)) +* **internal:** add warning about implementing interface ([5476caf](https://github.com/anthropics/anthropic-sdk-csharp/commit/5476cafac1904b8185fecd56ebbe088136df3ccd)) + + +### Refactors + +* **client:** flatten service namespaces ([8de3f66](https://github.com/anthropics/anthropic-sdk-csharp/commit/8de3f666532cf1ed31031587c4819e024e3bfb6f)) +* **client:** improve names of some types ([2e52d59](https://github.com/anthropics/anthropic-sdk-csharp/commit/2e52d5996dd0121814b2827eafa3a6fca6f5c3d9)) +* **client:** move some defaults out of `ClientOptions` ([d536293](https://github.com/anthropics/anthropic-sdk-csharp/commit/d536293d0cc42d3341437f390587907cc4a8df5e)) +* **client:** pass around `ClientOptions` instead of client ([608310d](https://github.com/anthropics/anthropic-sdk-csharp/commit/608310d02a14ccfdaefad3c0f8d921ed98c2375e)) + +## 0.2.0 (2025-11-05) + +Full Changelog: [v0.1.0...v0.2.0](https://github.com/anthropics/anthropic-sdk-csharp/compare/v0.1.0...v0.2.0) + +### ⚠ BREAKING CHANGES + +* **client:** make models immutable + +### Features + +* **api:** add ability to clear thinking in context management ([05d2ce6](https://github.com/anthropics/anthropic-sdk-csharp/commit/05d2ce6bc64fe547fe7bc695d383af89caf7a45d)) +* **client:** add response validation option ([6130f1b](https://github.com/anthropics/anthropic-sdk-csharp/commit/6130f1bc759bcc6c54cac411f69dd237c7fb40ce)) +* **client:** add support for option modification ([e105fba](https://github.com/anthropics/anthropic-sdk-csharp/commit/e105fbad5f26c737c57ce23ad2cbcd81b89bd07e)) +* **client:** make models immutable ([f55629c](https://github.com/anthropics/anthropic-sdk-csharp/commit/f55629c40cf51fc43cf3a64ec87e53051f88fee6)) +* **client:** support request timeout ([7411046](https://github.com/anthropics/anthropic-sdk-csharp/commit/7411046b4bc02671bd805d96a6c2745df0af4fcc)) + + +### Chores + +* **api:** mark older sonnet models as deprecated ([fc00d2b](https://github.com/anthropics/anthropic-sdk-csharp/commit/fc00d2b1dd5f100e523acf6f440e7a32c2452576)) +* **client:** simplify field validations ([6130f1b](https://github.com/anthropics/anthropic-sdk-csharp/commit/6130f1bc759bcc6c54cac411f69dd237c7fb40ce)) +* **internal:** codegen related update ([2798e0a](https://github.com/anthropics/anthropic-sdk-csharp/commit/2798e0a5fdc81a6076d449a73e8e880eb451b500)) +* **internal:** extract `ClientOptions` struct ([7e906c8](https://github.com/anthropics/anthropic-sdk-csharp/commit/7e906c854b0b68e981565df411407039dc6486e9)) +* **internal:** full qualify some references ([8a52868](https://github.com/anthropics/anthropic-sdk-csharp/commit/8a528685fbb605a06427773868638ebdcecb97b6)) + + +### Documentation + +* **client:** document `WithOptions` ([38352b0](https://github.com/anthropics/anthropic-sdk-csharp/commit/38352b0ec8b3b1d1f98ef08e83437875440cb9ba)) +* **client:** document response validation ([0e9f728](https://github.com/anthropics/anthropic-sdk-csharp/commit/0e9f72869c1c85f3e116c17eae5422847e2615fb)) +* **client:** document timeout option ([80d8d7f](https://github.com/anthropics/anthropic-sdk-csharp/commit/80d8d7fa0f2251892ee6c17e99c9a8db04334321)) +* **client:** improve snippet formatting ([94dc213](https://github.com/anthropics/anthropic-sdk-csharp/commit/94dc21334c5caeb106f5d07971c92c8b4a45aa1a)) + +## 0.1.0 (2025-10-27) + +Full Changelog: [v0.0.1...v0.1.0](https://github.com/anthropics/anthropic-sdk-csharp/compare/v0.0.1...v0.1.0) + +### Features + +* **api:** add claude-opus-4-1-20250805 ([c38689c](https://github.com/anthropics/anthropic-sdk-csharp/commit/c38689ce56b61bd5259785cd0478c8cecdf01630)) +* **api:** add support for Search Result Content Blocks ([3300718](https://github.com/anthropics/anthropic-sdk-csharp/commit/33007185312999c941e9ece33dde30b397e1b2ec)) +* **api:** adding support for agent skills ([4acc546](https://github.com/anthropics/anthropic-sdk-csharp/commit/4acc546f3d2117c098bf5eada070a83e619dbe5f)) +* **api:** adds support for Claude Sonnet 4.5 and context management features ([bab904c](https://github.com/anthropics/anthropic-sdk-csharp/commit/bab904c771612cde421696bda8616819024e863e)) +* **api:** adds support for Documents in tool results ([a7b5086](https://github.com/anthropics/anthropic-sdk-csharp/commit/a7b5086b8dd0211e723b4d6f9b903091df387d37)) +* **api:** adds support for text_editor_20250728 tool ([159d728](https://github.com/anthropics/anthropic-sdk-csharp/commit/159d7280cc3347b2241833ec32e64ddd8d467fbf)) +* **api:** adds support for web_fetch_20250910 tool ([74a7a92](https://github.com/anthropics/anthropic-sdk-csharp/commit/74a7a923abf5eef3ba34d6b2dda23a0e038d1064)) +* **api:** makes 1 hour TTL Cache Control generally available ([84b1ad3](https://github.com/anthropics/anthropic-sdk-csharp/commit/84b1ad3530ecf8f6fdb3c6dcd12e9a6331add9b4)) +* **api:** manual updates ([1528d71](https://github.com/anthropics/anthropic-sdk-csharp/commit/1528d714aee94bec3e0218e3f12d207fb5178878)) +* **api:** removed older deprecated models ([f5aafba](https://github.com/anthropics/anthropic-sdk-csharp/commit/f5aafbabd37dce4c3d14e3a8925bd9fde926bbd3)) +* **api:** search result content blocks ([e4368ee](https://github.com/anthropics/anthropic-sdk-csharp/commit/e4368ee1df5de9963ecd5295db7adaa2f882b776)) +* **api:** update PHP and C# ([d63878a](https://github.com/anthropics/anthropic-sdk-csharp/commit/d63878a830159b05ad5262de680cbd3c1cd1dd99)) +* **api:** update to desired NuGet name ([c4b6820](https://github.com/anthropics/anthropic-sdk-csharp/commit/c4b682000227c3daf1b6c854f7b4b3fe316aec45)) +* **betas:** add context-1m-2025-08-07 ([f65802a](https://github.com/anthropics/anthropic-sdk-csharp/commit/f65802a33c9474d32774a4aabae84ff53403acf8)) +* **ci:** add publishing flow for nuget ([487ac2e](https://github.com/anthropics/anthropic-sdk-csharp/commit/487ac2e31527626cf2105bb3209faa49ddb1654a)) +* **ci:** implement test/lint ci ([b34d54a](https://github.com/anthropics/anthropic-sdk-csharp/commit/b34d54ab994e80cb9a57721bfef817f857b4a0b9)) +* **client:** add and set all client ops ([3dee455](https://github.com/anthropics/anthropic-sdk-csharp/commit/3dee45538cd1f65cfa6da729ab9c3e6b47dafab7)) +* **client:** add implicit conversions to enums ([324f263](https://github.com/anthropics/anthropic-sdk-csharp/commit/324f263ccdee745b3f815abb17c09310146e56c0)) +* **client:** add some convenience constructors ([e2541e1](https://github.com/anthropics/anthropic-sdk-csharp/commit/e2541e10315a9304f4925fdafffc2494ab62a20f)) +* **client:** add streaming methods ([b394064](https://github.com/anthropics/anthropic-sdk-csharp/commit/b394064caef025f0a8cacfc299dc1dbe9636b1c8)) +* **client:** add switch and match helpers for unions ([d44a80c](https://github.com/anthropics/anthropic-sdk-csharp/commit/d44a80c8872f1fca137fbbfb4ed41c178ebe3c35)) +* **client:** adds support for code-execution-2025-08-26 tool ([5be3c78](https://github.com/anthropics/anthropic-sdk-csharp/commit/5be3c787f331d2dcaae55f1ed900b6cc04052818)) +* **client:** allow omitting all params object when all optional ([68a792f](https://github.com/anthropics/anthropic-sdk-csharp/commit/68a792f6591d02d8fce140949831a84b21eed686)) +* **client:** automatically set constants for user ([bb1343e](https://github.com/anthropics/anthropic-sdk-csharp/commit/bb1343ef5311c535a0836e83c65e156483eb4a45)) +* **client:** basic paginated endpoint support ([4766f1e](https://github.com/anthropics/anthropic-sdk-csharp/commit/4766f1ec369b01863ce96a22264f40d9f953f412)) +* **client:** implement implicit union casts ([e36b8fa](https://github.com/anthropics/anthropic-sdk-csharp/commit/e36b8fa372c81c387298bd2e700a74a0dac2c8d1)) +* **client:** improve model names ([18a0af9](https://github.com/anthropics/anthropic-sdk-csharp/commit/18a0af9f5d5eca5e0b1267c213e35d748ca3a0a0)) +* **client:** improve signature of `trypickx` methods ([620b39b](https://github.com/anthropics/anthropic-sdk-csharp/commit/620b39bd653c5c5fbdf3ddd0d8bfe3921ec9c81f)) +* **client:** make union deserialization more robust ([26d42da](https://github.com/anthropics/anthropic-sdk-csharp/commit/26d42dae0039f709e4ca33449c9567bbc0ff689b)) +* **client:** make union deserialization more robust ([f85bc36](https://github.com/anthropics/anthropic-sdk-csharp/commit/f85bc367ad3f076d36b233cc956768fea226d1ae)) +* **client:** refactor exceptions ([e5cfd36](https://github.com/anthropics/anthropic-sdk-csharp/commit/e5cfd364afd96ce37f01a639a6587e7c27801715)) +* **client:** refactor unions ([f6b60e3](https://github.com/anthropics/anthropic-sdk-csharp/commit/f6b60e3e4ce82b5442d27989f751c86de0354fc2)) +* **client:** shorten union variant names ([c397c9b](https://github.com/anthropics/anthropic-sdk-csharp/commit/c397c9bda8cfde000e9b092fb0f384695a9993cd)) +* **internal:** add dedicated build job in ci ([9d46238](https://github.com/anthropics/anthropic-sdk-csharp/commit/9d46238a5bfc3c25276ed63bcc55b26aa42674d7)) +* **internal:** add dev container ([e7682c0](https://github.com/anthropics/anthropic-sdk-csharp/commit/e7682c0790e1adbe4b24c9c6cadfb2c6c7c43112)) +* **internal:** allow overriding mock url via `TEST_API_BASE_URL` env ([f14a23c](https://github.com/anthropics/anthropic-sdk-csharp/commit/f14a23c5b6065a377bf273189c5cf4d5b1826250)) +* **internal:** generate release flow files ([7a759d7](https://github.com/anthropics/anthropic-sdk-csharp/commit/7a759d76d63bd673defaa8a00aeb9c1111ce20a4)) + + +### Bug Fixes + +* **client:** better type names ([057bf2d](https://github.com/anthropics/anthropic-sdk-csharp/commit/057bf2ddf817d443f86fe5913cf5399705c65914)) +* **client:** compilation error ([56d1c41](https://github.com/anthropics/anthropic-sdk-csharp/commit/56d1c41dbcca95ddbd40cb296ebe516a3598b30d)) +* **client:** handle multiple auth options gracefully ([beabac5](https://github.com/anthropics/anthropic-sdk-csharp/commit/beabac5836af2a6bb946605d978cdc1325912aba)) +* **client:** improve model validation ([b77753e](https://github.com/anthropics/anthropic-sdk-csharp/commit/b77753e46cad3eda6ef37f4ad2df2066199b1a14)) +* **client:** instantiate union variant from list properly ([0db37e5](https://github.com/anthropics/anthropic-sdk-csharp/commit/0db37e5874d4a361048feac13014f25740e5142a)) +* **client:** support non-optional client options ([fadaa63](https://github.com/anthropics/anthropic-sdk-csharp/commit/fadaa63599a9411094aede97aa59084916a3de6d)) +* **docs:** re-order using statements ([b77bdb2](https://github.com/anthropics/anthropic-sdk-csharp/commit/b77bdb2aa4bcde1a0e21938c1d4be5ea755dfaed)) +* **internal:** add message to sse exception ([8481832](https://github.com/anthropics/anthropic-sdk-csharp/commit/8481832fd8861b4f1ec9ed46389716ce0be4589c)) +* **internal:** minor bug fixes on model instantiation and union validation ([6d0f0d9](https://github.com/anthropics/anthropic-sdk-csharp/commit/6d0f0d9b399fb1e270f215d130e9e59b37bec627)) +* **internal:** prefer to use implicit instantiation when possible ([b869753](https://github.com/anthropics/anthropic-sdk-csharp/commit/b86975337839d95e151e27421c84566ad0c6ecd7)) +* **internal:** remove example csproj ([e6e2c93](https://github.com/anthropics/anthropic-sdk-csharp/commit/e6e2c932f4ac99d7dacef0fad4177f0d0d76c9f2)) +* **internal:** remove unused null class ([c46f844](https://github.com/anthropics/anthropic-sdk-csharp/commit/c46f844118f54ca85615794d420c8b4202761f27)) +* **internal:** rename package directory ([a2557ac](https://github.com/anthropics/anthropic-sdk-csharp/commit/a2557ac8a9567267147d2d4f296c674f74460b82)) +* **internal:** various minor code fixes ([136162a](https://github.com/anthropics/anthropic-sdk-csharp/commit/136162addc0812087d051e8e5844226f31eda895)) + + +### Chores + +* **api:** remove unsupported endpoints ([d318ba7](https://github.com/anthropics/anthropic-sdk-csharp/commit/d318ba7c3c652b813fe81316ac5d5110fd8ebcb2)) +* **api:** update BetaCitationSearchResultLocation ([801a222](https://github.com/anthropics/anthropic-sdk-csharp/commit/801a222c8eeaa43625bdc078ef9da8ffec9351e4)) +* **client:** add context-management-2025-06-27 beta header ([c716a85](https://github.com/anthropics/anthropic-sdk-csharp/commit/c716a85034072a14e1c189ca2422f6ec5fce680b)) +* **client:** add model-context-window-exceeded-2025-08-26 beta header ([6ea4ac3](https://github.com/anthropics/anthropic-sdk-csharp/commit/6ea4ac36590316c30a7622f1cf67ce5dd473ed7e)) +* **client:** add TextEditor_20250429 tool ([adee5b4](https://github.com/anthropics/anthropic-sdk-csharp/commit/adee5b42af4ac04e3569570aca45a931aa16dd6f)) +* **client:** make some interfaces internal ([476e69e](https://github.com/anthropics/anthropic-sdk-csharp/commit/476e69e077869ce56271dfe69837a02ea1d66811)) +* **client:** swap `[@params](https://github.com/params)` to better name ([3d8e0d9](https://github.com/anthropics/anthropic-sdk-csharp/commit/3d8e0d96ba2e7e6d1c2aaf4da3848647bd6d5e1f)) +* **docs:** clarify beta library limitations in readme ([0aafa74](https://github.com/anthropics/anthropic-sdk-csharp/commit/0aafa74d0d8d2e4664033eacb248688aab52247b)) +* improve example values ([7b3bc97](https://github.com/anthropics/anthropic-sdk-csharp/commit/7b3bc9703a5d189f5a7b41a96e91efb5463e0e8e)) +* **internal:** codegen related update ([b98acb4](https://github.com/anthropics/anthropic-sdk-csharp/commit/b98acb42e3fe9bae70c6a799e48f914019e003b1)) +* **internal:** codegen related update ([c765e20](https://github.com/anthropics/anthropic-sdk-csharp/commit/c765e20eada019988d7d13597258f5eff28431e8)) +* **internal:** codegen related update ([fb6b738](https://github.com/anthropics/anthropic-sdk-csharp/commit/fb6b7383219e9fef56cdf0786170f1943249b9c7)) +* **internal:** codegen related update ([135523a](https://github.com/anthropics/anthropic-sdk-csharp/commit/135523aad5f9df5ee22a25f4ba7670335f2b8647)) +* **internal:** fix tests ([c7205c2](https://github.com/anthropics/anthropic-sdk-csharp/commit/c7205c25c86ce6f61d49a97d24827c21853f4d19)) +* **internal:** refactor tests to de-duplicate client instantiation logic ([f14a23c](https://github.com/anthropics/anthropic-sdk-csharp/commit/f14a23c5b6065a377bf273189c5cf4d5b1826250)) +* **internal:** remove unnecessary internal aliasing ([d210122](https://github.com/anthropics/anthropic-sdk-csharp/commit/d2101221fc498b57c60593896491751a6c77f9d8)) +* **internal:** rename parameters ([0013847](https://github.com/anthropics/anthropic-sdk-csharp/commit/0013847d2d7db6f4611b6c863f74b11a442310a1)) +* **internal:** restructure some imports ([974e4a3](https://github.com/anthropics/anthropic-sdk-csharp/commit/974e4a31bde9f9e64e8115fd0198baa4342603c7)) +* **internal:** stop running whitespace lint ([f14a23c](https://github.com/anthropics/anthropic-sdk-csharp/commit/f14a23c5b6065a377bf273189c5cf4d5b1826250)) +* **internal:** update comment in script ([d9ff761](https://github.com/anthropics/anthropic-sdk-csharp/commit/d9ff7619e8a211f948913945e3f3d2b94a122611)) +* **internal:** update test skipping reason ([124aab3](https://github.com/anthropics/anthropic-sdk-csharp/commit/124aab31ade145f7e326483f6ffc4aeda8005fe1)) +* **internal:** use nicer generic names ([00c3c7e](https://github.com/anthropics/anthropic-sdk-csharp/commit/00c3c7e215233ff0882930db8dc8177c22b85165)) +* rename some things ([654eb75](https://github.com/anthropics/anthropic-sdk-csharp/commit/654eb75cd6097c1554d07e2ec81da2c212e395be)) +* update @stainless-api/prism-cli to v5.15.0 ([3a1d8f7](https://github.com/anthropics/anthropic-sdk-csharp/commit/3a1d8f7920630ca2111f401d0c4792ba324135ff)) +* update formatting ([8b06f4f](https://github.com/anthropics/anthropic-sdk-csharp/commit/8b06f4f14153b608acbe1f00461a055e3c74d553)) +* update SDK settings ([f5e0568](https://github.com/anthropics/anthropic-sdk-csharp/commit/f5e05681a49e4de0d8cc3f73e08d9590997c27a6)) +* use non-aliased `using` ([ba9d1ac](https://github.com/anthropics/anthropic-sdk-csharp/commit/ba9d1ac2f5b3e86dc4fcf9f5857e550a40ec8995)) + + +### Documentation + +* add more info to the readme ([9f20bf2](https://github.com/anthropics/anthropic-sdk-csharp/commit/9f20bf26184307069b94c81d219d732ac46ace50)) +* **client:** add more property comments ([a3e973b](https://github.com/anthropics/anthropic-sdk-csharp/commit/a3e973b0e6d057e58e6f0bd08c8a5635da896974)) +* fix installation instructions ([4c76768](https://github.com/anthropics/anthropic-sdk-csharp/commit/4c767688eca1a4a873c8f80e266c1600bfd4bafa)) +* note alpha status ([cc023e3](https://github.com/anthropics/anthropic-sdk-csharp/commit/cc023e3d5096fc5bdb08f86f85c3afd71090159a)) +* streaming in readme ([6063490](https://github.com/anthropics/anthropic-sdk-csharp/commit/6063490d142965cf0be2d937e4d39f5d624a5b84)) + + +### Refactors + +* **client:** refine enum representation ([a3e973b](https://github.com/anthropics/anthropic-sdk-csharp/commit/a3e973b0e6d057e58e6f0bd08c8a5635da896974)) +* **client:** use plural for service namespace ([843da53](https://github.com/anthropics/anthropic-sdk-csharp/commit/843da53c91a4e925298aae8907f8990b7e13de9e)) +>>>>>>> origin/generated--merge-conflict diff --git a/README.md b/README.md index fe689450..5e5d8462 100644 --- a/README.md +++ b/README.md @@ -24,6 +24,8 @@ The REST API documentation can be found on [docs.anthropic.com](https://docs.ant ## Installation +Install the package from [NuGet](https://www.nuget.org/packages/Anthropic): + ```bash dotnet add package Anthropic ``` diff --git a/examples/Anthropic.Beta.ClientExample/Anthropic.Beta.ClientExample.csproj b/examples/Anthropic.Beta.ClientExample/Anthropic.Beta.ClientExample.csproj deleted file mode 100644 index 76a262de..00000000 --- a/examples/Anthropic.Beta.ClientExample/Anthropic.Beta.ClientExample.csproj +++ /dev/null @@ -1,12 +0,0 @@ - - - - - - Exe - net8.0 - Anthropic.Beta.ClientExample - enable - disable - - diff --git a/examples/Anthropic.ClientExample/Anthropic.ClientExample.csproj b/examples/Anthropic.ClientExample/Anthropic.ClientExample.csproj deleted file mode 100644 index b973a978..00000000 --- a/examples/Anthropic.ClientExample/Anthropic.ClientExample.csproj +++ /dev/null @@ -1,12 +0,0 @@ - - - - - - Exe - net8.0 - Anthropic.ClientExample - enable - disable - - diff --git a/examples/Anthropic.Examples.sln b/examples/Anthropic.Examples.sln index 2362337d..c5f116ad 100644 --- a/examples/Anthropic.Examples.sln +++ b/examples/Anthropic.Examples.sln @@ -5,6 +5,14 @@ VisualStudioVersion = 17.0.31903.59 MinimumVisualStudioVersion = 10.0.40219.1 Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MessagesExample", "MessagesExample\MessagesExample.csproj", "{FA9BAC30-CC15-4D21-99CF-011D5D082FAF}" EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ThinkingStreamingExample", "ThinkingStreamingExample\ThinkingStreamingExample.csproj", "{97BE49BD-B144-4967-8718-C79E4521BA3F}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ThinkingExample", "ThinkingExample\ThinkingExample.csproj", "{79DCA526-628F-413B-83DA-F1B92029C065}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MessagesStreamingExample", "MessagesStreamingExample\MessagesStreamingExample.csproj", "{8CD54CE9-894F-4636-8CAF-D20914CF4014}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ChatClientExample", "ChatClientExample\ChatClientExample.csproj", "{AA6ED2E6-A693-4FD8-AF20-1D339FBFBF96}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU @@ -27,6 +35,54 @@ Global {FA9BAC30-CC15-4D21-99CF-011D5D082FAF}.Release|x64.Build.0 = Release|Any CPU {FA9BAC30-CC15-4D21-99CF-011D5D082FAF}.Release|x86.ActiveCfg = Release|Any CPU {FA9BAC30-CC15-4D21-99CF-011D5D082FAF}.Release|x86.Build.0 = Release|Any CPU + {97BE49BD-B144-4967-8718-C79E4521BA3F}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {97BE49BD-B144-4967-8718-C79E4521BA3F}.Debug|Any CPU.Build.0 = Debug|Any CPU + {97BE49BD-B144-4967-8718-C79E4521BA3F}.Debug|x64.ActiveCfg = Debug|Any CPU + {97BE49BD-B144-4967-8718-C79E4521BA3F}.Debug|x64.Build.0 = Debug|Any CPU + {97BE49BD-B144-4967-8718-C79E4521BA3F}.Debug|x86.ActiveCfg = Debug|Any CPU + {97BE49BD-B144-4967-8718-C79E4521BA3F}.Debug|x86.Build.0 = Debug|Any CPU + {97BE49BD-B144-4967-8718-C79E4521BA3F}.Release|Any CPU.ActiveCfg = Release|Any CPU + {97BE49BD-B144-4967-8718-C79E4521BA3F}.Release|Any CPU.Build.0 = Release|Any CPU + {97BE49BD-B144-4967-8718-C79E4521BA3F}.Release|x64.ActiveCfg = Release|Any CPU + {97BE49BD-B144-4967-8718-C79E4521BA3F}.Release|x64.Build.0 = Release|Any CPU + {97BE49BD-B144-4967-8718-C79E4521BA3F}.Release|x86.ActiveCfg = Release|Any CPU + {97BE49BD-B144-4967-8718-C79E4521BA3F}.Release|x86.Build.0 = Release|Any CPU + {79DCA526-628F-413B-83DA-F1B92029C065}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {79DCA526-628F-413B-83DA-F1B92029C065}.Debug|Any CPU.Build.0 = Debug|Any CPU + {79DCA526-628F-413B-83DA-F1B92029C065}.Debug|x64.ActiveCfg = Debug|Any CPU + {79DCA526-628F-413B-83DA-F1B92029C065}.Debug|x64.Build.0 = Debug|Any CPU + {79DCA526-628F-413B-83DA-F1B92029C065}.Debug|x86.ActiveCfg = Debug|Any CPU + {79DCA526-628F-413B-83DA-F1B92029C065}.Debug|x86.Build.0 = Debug|Any CPU + {79DCA526-628F-413B-83DA-F1B92029C065}.Release|Any CPU.ActiveCfg = Release|Any CPU + {79DCA526-628F-413B-83DA-F1B92029C065}.Release|Any CPU.Build.0 = Release|Any CPU + {79DCA526-628F-413B-83DA-F1B92029C065}.Release|x64.ActiveCfg = Release|Any CPU + {79DCA526-628F-413B-83DA-F1B92029C065}.Release|x64.Build.0 = Release|Any CPU + {79DCA526-628F-413B-83DA-F1B92029C065}.Release|x86.ActiveCfg = Release|Any CPU + {79DCA526-628F-413B-83DA-F1B92029C065}.Release|x86.Build.0 = Release|Any CPU + {8CD54CE9-894F-4636-8CAF-D20914CF4014}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {8CD54CE9-894F-4636-8CAF-D20914CF4014}.Debug|Any CPU.Build.0 = Debug|Any CPU + {8CD54CE9-894F-4636-8CAF-D20914CF4014}.Debug|x64.ActiveCfg = Debug|Any CPU + {8CD54CE9-894F-4636-8CAF-D20914CF4014}.Debug|x64.Build.0 = Debug|Any CPU + {8CD54CE9-894F-4636-8CAF-D20914CF4014}.Debug|x86.ActiveCfg = Debug|Any CPU + {8CD54CE9-894F-4636-8CAF-D20914CF4014}.Debug|x86.Build.0 = Debug|Any CPU + {8CD54CE9-894F-4636-8CAF-D20914CF4014}.Release|Any CPU.ActiveCfg = Release|Any CPU + {8CD54CE9-894F-4636-8CAF-D20914CF4014}.Release|Any CPU.Build.0 = Release|Any CPU + {8CD54CE9-894F-4636-8CAF-D20914CF4014}.Release|x64.ActiveCfg = Release|Any CPU + {8CD54CE9-894F-4636-8CAF-D20914CF4014}.Release|x64.Build.0 = Release|Any CPU + {8CD54CE9-894F-4636-8CAF-D20914CF4014}.Release|x86.ActiveCfg = Release|Any CPU + {8CD54CE9-894F-4636-8CAF-D20914CF4014}.Release|x86.Build.0 = Release|Any CPU + {AA6ED2E6-A693-4FD8-AF20-1D339FBFBF96}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {AA6ED2E6-A693-4FD8-AF20-1D339FBFBF96}.Debug|Any CPU.Build.0 = Debug|Any CPU + {AA6ED2E6-A693-4FD8-AF20-1D339FBFBF96}.Debug|x64.ActiveCfg = Debug|Any CPU + {AA6ED2E6-A693-4FD8-AF20-1D339FBFBF96}.Debug|x64.Build.0 = Debug|Any CPU + {AA6ED2E6-A693-4FD8-AF20-1D339FBFBF96}.Debug|x86.ActiveCfg = Debug|Any CPU + {AA6ED2E6-A693-4FD8-AF20-1D339FBFBF96}.Debug|x86.Build.0 = Debug|Any CPU + {AA6ED2E6-A693-4FD8-AF20-1D339FBFBF96}.Release|Any CPU.ActiveCfg = Release|Any CPU + {AA6ED2E6-A693-4FD8-AF20-1D339FBFBF96}.Release|Any CPU.Build.0 = Release|Any CPU + {AA6ED2E6-A693-4FD8-AF20-1D339FBFBF96}.Release|x64.ActiveCfg = Release|Any CPU + {AA6ED2E6-A693-4FD8-AF20-1D339FBFBF96}.Release|x64.Build.0 = Release|Any CPU + {AA6ED2E6-A693-4FD8-AF20-1D339FBFBF96}.Release|x86.ActiveCfg = Release|Any CPU + {AA6ED2E6-A693-4FD8-AF20-1D339FBFBF96}.Release|x86.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE diff --git a/examples/MessagesExample/Program.cs b/examples/MessagesExample/Program.cs index 6c8b0fc2..fa724119 100644 --- a/examples/MessagesExample/Program.cs +++ b/examples/MessagesExample/Program.cs @@ -1,10 +1,8 @@ -using System; -using Anthropic; -using Anthropic.Foundry; +using Anthropic; using Anthropic.Models.Messages; // Configured using the ANTHROPIC_API_KEY, ANTHROPIC_AUTH_TOKEN and ANTHROPIC_BASE_URL environment variables -IAnthropicClient client = new AnthropicClient(); +var client = new AnthropicClient(); // For using the Foundry client, use this instead // AnthropicFoundryClient client = new(new AnthropicFoundryApiKeyCredentials("API-TOKEN", "RESOURCE-NAME")); @@ -21,7 +19,7 @@ var response = await client.Messages.Create(parameters); -var message = String.Join( +var message = string.Join( "", response .Content.Where(message => message.Value is TextBlock) diff --git a/examples/MessagesStreamingExample/Program.cs b/examples/MessagesStreamingExample/Program.cs index 9c803716..7135a31f 100644 --- a/examples/MessagesStreamingExample/Program.cs +++ b/examples/MessagesStreamingExample/Program.cs @@ -1,8 +1,5 @@ -using System; -using Anthropic; +using Anthropic; using Anthropic.Models.Messages; -using Anthropic.Models.Messages.ContentBlockVariants; -using Anthropic.Models.Messages.MessageParamProperties; // Configured using the ANTHROPIC_API_KEY, ANTHROPIC_AUTH_TOKEN and ANTHROPIC_BASE_URL environment variables AnthropicClient client = new(); diff --git a/examples/ThinkingExample/Program.cs b/examples/ThinkingExample/Program.cs index 18ecef7c..888588e1 100644 --- a/examples/ThinkingExample/Program.cs +++ b/examples/ThinkingExample/Program.cs @@ -1,8 +1,5 @@ -using System; -using Anthropic; +using Anthropic; using Anthropic.Models.Messages; -using Anthropic.Models.Messages.MessageParamProperties; -using ContentBlockVariants = Anthropic.Models.Messages.ContentBlockVariants; // Configured using the ANTHROPIC_API_KEY, ANTHROPIC_AUTH_TOKEN and ANTHROPIC_BASE_URL environment variables AnthropicClient client = new(); @@ -22,21 +19,19 @@ foreach (ContentBlock block in response.Content) { - if (block.TryPickThinking(out ThinkingBlock thinking)) + if (block.TryPickThinking(out ThinkingBlock? thinking)) { Console.WriteLine($"Thinking: {thinking.Thinking}"); } - else if (block.TryPickText(out TextBlock text)) + else if (block.TryPickText(out TextBlock? text)) { Console.WriteLine($"Text: {text.Text}"); } } -var message = String.Join( +var message = string.Join( "", - response - .Content.OfType() - .Select((textBlock) => textBlock.Value.Text) + response.Content.Select(e => e.Value).OfType().Select((textBlock) => textBlock.Text) ); Console.WriteLine(message); diff --git a/examples/ThinkingStreamingExample/Program.cs b/examples/ThinkingStreamingExample/Program.cs index cb15d3fa..f965b96e 100644 --- a/examples/ThinkingStreamingExample/Program.cs +++ b/examples/ThinkingStreamingExample/Program.cs @@ -1,7 +1,5 @@ -using System; -using Anthropic; +using Anthropic; using Anthropic.Models.Messages; -using Anthropic.Models.Messages.MessageParamProperties; // Configured using the ANTHROPIC_API_KEY, ANTHROPIC_AUTH_TOKEN and ANTHROPIC_BASE_URL environment variables AnthropicClient client = new(); diff --git a/release-please-config.json b/release-please-config.json index 2a1838bc..779d38a8 100644 --- a/release-please-config.json +++ b/release-please-config.json @@ -1,6 +1,6 @@ { "packages": { - ".": {}, + "src/Anthropic": {}, "src/Anthropic.Foundry": {} }, "$schema": "https://raw.githubusercontent.com/stainless-api/release-please/main/schemas/config.json", @@ -60,7 +60,7 @@ "hidden": true } ], - "release-type": "simple", + "release-type": "csharp", "extra-files": [ { "type": "xml", diff --git a/scripts/build b/scripts/build index 3ce1e776..ab5f1179 100755 --- a/scripts/build +++ b/scripts/build @@ -5,4 +5,5 @@ set -e cd "$(dirname "$0")/.." echo "==> Running dotnet build" -dotnet build +dotnet build Anthropic.sln +dotnet build examples/Anthropic.Examples.sln diff --git a/src/Anthropic.Foundry/Anthropic.Foundry.csproj b/src/Anthropic.Foundry/Anthropic.Foundry.csproj index a9f2825b..2f453e21 100644 --- a/src/Anthropic.Foundry/Anthropic.Foundry.csproj +++ b/src/Anthropic.Foundry/Anthropic.Foundry.csproj @@ -20,7 +20,7 @@ true true Anthropic.Foundry - 0.1.0 + 0.2.0 Stainless Software, Inc. Stainless Software, Inc. https://github.com/anthropics/anthropic-sdk-csharp diff --git a/src/Anthropic.Foundry/CHANGELOG.md b/src/Anthropic.Foundry/CHANGELOG.md index 1a34dc64..e11a8574 100644 --- a/src/Anthropic.Foundry/CHANGELOG.md +++ b/src/Anthropic.Foundry/CHANGELOG.md @@ -1,5 +1,34 @@ # Changelog +## 0.2.0 (2025-12-10) + +Full Changelog: [Foundry-v0.1.0...Foundry-v0.2.0](https://github.com/anthropics/anthropic-sdk-csharp/compare/Foundry-v0.1.0...Foundry-v0.2.0) + +### Features + +* add Foundry client ([5f87e12](https://github.com/anthropics/anthropic-sdk-csharp/commit/5f87e129a262d8a373e5e10bcca4196cf5db0394)) +* **client:** additional methods for positional params ([08c27c6](https://github.com/anthropics/anthropic-sdk-csharp/commit/08c27c6a4cb45b886be44babbb51bf4934add374)) +* **client:** additional methods for positional params ([8bc6323](https://github.com/anthropics/anthropic-sdk-csharp/commit/8bc6323c38ce551f995bec5e4b1584460b7f037b)) + + +### Bug Fixes + +* **client:** return correct type for foundry#WithOptions ([#18](https://github.com/anthropics/anthropic-sdk-csharp/issues/18)) ([9ff2124](https://github.com/anthropics/anthropic-sdk-csharp/commit/9ff2124a9190269ff4a469b6e8c9f6b895f8d2d2)) +* **client:** return correct type for foundry#WithOptions ([#18](https://github.com/anthropics/anthropic-sdk-csharp/issues/18)) ([f814a46](https://github.com/anthropics/anthropic-sdk-csharp/commit/f814a460503abf7fdf7a824b5bf446ef74d60f28)) +* **internal:** remove release notes from foundry readme ([afeaa2f](https://github.com/anthropics/anthropic-sdk-csharp/commit/afeaa2f526c3818c244bb351b4dad56a59883395)) +* use correct versions ([7c97d7f](https://github.com/anthropics/anthropic-sdk-csharp/commit/7c97d7f19c6937a2dacb666b05b9b9d040d677c7)) +* use correct versions ([c78c8db](https://github.com/anthropics/anthropic-sdk-csharp/commit/c78c8db4b6effa6b1438bb879bcafdad2d155808)) + + +### Chores + +* fix ci ([#196](https://github.com/anthropics/anthropic-sdk-csharp/issues/196)) ([8dede61](https://github.com/anthropics/anthropic-sdk-csharp/commit/8dede6176cb86e1ae85db9c8d0fae50c595ef964)) +* **internal:** add logo to nuget package ([#181](https://github.com/anthropics/anthropic-sdk-csharp/issues/181)) ([e01f08d](https://github.com/anthropics/anthropic-sdk-csharp/commit/e01f08dbd35f05c3ecc964eb040312b4f7ca6713)) +* **internal:** suppress diagnostic for .netstandard2.0 ([9ede62d](https://github.com/anthropics/anthropic-sdk-csharp/commit/9ede62de370abcad1fc1a5211700a6c967d360ca)) +* **internal:** suppress diagnostic for .netstandard2.0 ([1b0714d](https://github.com/anthropics/anthropic-sdk-csharp/commit/1b0714dc78ba2e69ab149d7cf768963379ec73e5)) +* sync with release-please ([2f5aa29](https://github.com/anthropics/anthropic-sdk-csharp/commit/2f5aa2992a2d462bb1f547efa09355e4f0b60656)) +* sync with release-please ([191236b](https://github.com/anthropics/anthropic-sdk-csharp/commit/191236bf5fb39092a2e2afc062e9cd222b859d2d)) + ## 0.1.0 (2025-12-01) Full Changelog: [v0.0.3...v0.1.0](https://github.com/anthropics/anthropic-sdk-csharp/compare/v0.0.3...v0.1.0) diff --git a/src/Anthropic.Tests/AnthropicClientBetaExtensionsTests.cs b/src/Anthropic.Tests/AnthropicClientBetaExtensionsTests.cs index a1b39eba..c4db4d0d 100644 --- a/src/Anthropic.Tests/AnthropicClientBetaExtensionsTests.cs +++ b/src/Anthropic.Tests/AnthropicClientBetaExtensionsTests.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Linq; using System.Text.Json; using System.Threading.Tasks; using Anthropic; @@ -1128,7 +1129,9 @@ public async Task GetResponseAsync_WithAIFunctionTool_AdditionalProperties_Flows { new() { ["query"] = JsonSerializer.SerializeToElement("example query") }, }, - [nameof(BetaTool.AllowedCallers)] = new List> + [nameof(BetaTool.AllowedCallers)] = new List< + ApiEnum + > { new(JsonSerializer.SerializeToElement("direct")), }, @@ -1210,4 +1213,902 @@ public async Task GetResponseAsync_WithAIFunctionTool_PartialAdditionalPropertie ChatResponse response = await chatClient.GetResponseAsync("Use strict tool", options); Assert.NotNull(response); } + + [Fact] + public void AsAITool_GetService_ReturnsToolUnion() + { + BetaToolUnion toolUnion = new BetaWebSearchTool20250305() + { + AllowedDomains = ["example.com"], + }; + AITool aiTool = toolUnion.AsAITool(); + Assert.Same(toolUnion, aiTool.GetService()); + + Assert.Null(aiTool.GetService("key")); + Assert.Null(aiTool.GetService()); + + Assert.Contains(nameof(BetaWebSearchTool20250305), aiTool.Name); + } + + [Fact] + public void AsAITool_GetService_ThrowsOnNullServiceType() + { + AITool aiTool = ( + (BetaToolUnion)new BetaWebSearchTool20250305() { AllowedDomains = ["example.com"] } + ).AsAITool(); + Assert.Throws(() => aiTool.GetService(null!, null)); + } + + [Fact] + public async Task GetResponseAsync_WithHostedFileContent() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "document", + "source": { + "type": "file", + "file_id": "file_abc123" + } + }] + }] + } + """, + actualResponse: """ + { + "id": "msg_hosted_file_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "text", + "text": "I read the hosted file." + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 20, + "output_tokens": 6 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + + var hostedFile = new HostedFileContent("file_abc123"); + + ChatResponse response = await chatClient.GetResponseAsync( + [new ChatMessage(ChatRole.User, [hostedFile])] + ); + Assert.NotNull(response); + } + + [Fact] + public async Task GetResponseAsync_WithHostedCodeInterpreterTool() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Execute code" + }] + }], + "tools": [{ + "type": "code_execution_20250825", + "name": "code_execution" + }] + } + """, + actualResponse: """ + { + "id": "msg_code_exec_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "text", + "text": "I can execute code." + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 15, + "output_tokens": 6 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + + ChatOptions options = new() { Tools = [new HostedCodeInterpreterTool()] }; + + ChatResponse response = await chatClient.GetResponseAsync("Execute code", options); + Assert.NotNull(response); + } + + [Fact] + public async Task GetResponseAsync_WithRawRepresentationFactory() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 2048, + "model": "claude-haiku-4-5", + "messages": [ + { + "role": "user", + "content": [{ + "type": "text", + "text": "Preconfigured message" + }] + }, + { + "role": "user", + "content": [{ + "type": "text", + "text": "New message" + }] + } + ] + } + """, + actualResponse: """ + { + "id": "msg_factory_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "text", + "text": "Response" + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 20, + "output_tokens": 5 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + + ChatOptions options = new() + { + RawRepresentationFactory = _ => new MessageCreateParams() + { + MaxTokens = 2048, + Model = "claude-haiku-4-5", + Messages = + [ + new BetaMessageParam() + { + Role = Role.User, + Content = new BetaMessageParamContent( + [new BetaTextBlockParam() { Text = "Preconfigured message" }] + ), + }, + ], + }, + }; + + ChatResponse response = await chatClient.GetResponseAsync("New message", options); + Assert.NotNull(response); + } + + [Fact] + public async Task GetResponseAsync_WithRawRepresentationFactory_SystemMessagesMerged() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Test" + }] + }], + "system": [ + { + "type": "text", + "text": "Existing system message" + }, + { + "type": "text", + "text": "New system message" + } + ] + } + """, + actualResponse: """ + { + "id": "msg_sys_merge_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "text", + "text": "Response" + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 15, + "output_tokens": 5 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + + ChatOptions options = new() + { + RawRepresentationFactory = _ => new MessageCreateParams() + { + MaxTokens = 1024, + Model = "claude-haiku-4-5", + Messages = [], + System = "Existing system message", + }, + }; + + ChatResponse response = await chatClient.GetResponseAsync( + [ + new ChatMessage(ChatRole.System, "New system message"), + new ChatMessage(ChatRole.User, "Test"), + ], + options + ); + Assert.NotNull(response); + } + + [Fact] + public async Task GetResponseAsync_WithRawRepresentationFactory_SystemMessagesListMerged() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Test" + }] + }], + "system": [ + { + "type": "text", + "text": "First" + }, + { + "type": "text", + "text": "Second" + }, + { + "type": "text", + "text": "Third" + } + ] + } + """, + actualResponse: """ + { + "id": "msg_sys_list_merge_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "text", + "text": "Response" + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 15, + "output_tokens": 5 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + + ChatOptions options = new() + { + RawRepresentationFactory = _ => new MessageCreateParams() + { + MaxTokens = 1024, + Model = "claude-haiku-4-5", + Messages = [], + System = new System.Collections.Generic.List + { + new() { Text = "First" }, + new() { Text = "Second" }, + }, + }, + }; + + ChatResponse response = await chatClient.GetResponseAsync( + [new ChatMessage(ChatRole.System, "Third"), new ChatMessage(ChatRole.User, "Test")], + options + ); + Assert.NotNull(response); + } + + [Fact] + public async Task GetResponseAsync_McpToolResultWithTextList() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Test MCP text list" + }] + }] + } + """, + actualResponse: """ + { + "id": "msg_mcp_text_list_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "mcp_tool_result", + "tool_use_id": "mcp_call_789", + "is_error": false, + "content": [{ + "type": "text", + "text": "First result" + }, { + "type": "text", + "text": "Second result" + }] + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 10, + "output_tokens": 15 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + ChatResponse response = await chatClient.GetResponseAsync("Test MCP text list"); + + McpServerToolResultContent mcpResult = Assert.IsType( + response.Messages[0].Contents[0] + ); + Assert.NotNull(mcpResult); + Assert.Equal("mcp_call_789", mcpResult.CallId); + Assert.NotNull(mcpResult.Output); + Assert.Equal(2, mcpResult.Output.Count); + Assert.Equal("First result", ((TextContent)mcpResult.Output[0]).Text); + Assert.Equal("Second result", ((TextContent)mcpResult.Output[1]).Text); + } + + [Fact] + public async Task GetResponseAsync_CodeExecutionResult_WithStdout() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Run code" + }] + }] + } + """, + actualResponse: """ + { + "id": "msg_code_stdout_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "code_execution_tool_result", + "tool_use_id": "code_exec_1", + "content": { + "type": "code_execution_result", + "stdout": "Hello World\n42\n", + "stderr": "", + "return_code": 0, + "content": [] + } + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 10, + "output_tokens": 5 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + ChatResponse response = await chatClient.GetResponseAsync("Run code"); + + CodeInterpreterToolResultContent codeResult = + Assert.IsType(response.Messages[0].Contents[0]); + Assert.NotNull(codeResult); + Assert.Equal("code_exec_1", codeResult.CallId); + Assert.NotNull(codeResult.Outputs); + Assert.Single(codeResult.Outputs); + + TextContent textOutput = Assert.IsType(codeResult.Outputs[0]); + Assert.Equal("Hello World\n42\n", textOutput.Text); + } + + [Fact] + public async Task GetResponseAsync_CodeExecutionResult_WithStderrAndNonZeroReturnCode() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Run failing code" + }] + }] + } + """, + actualResponse: """ + { + "id": "msg_code_stderr_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "code_execution_tool_result", + "tool_use_id": "code_exec_2", + "content": { + "type": "code_execution_result", + "stdout": "", + "stderr": "Division by zero error", + "return_code": 1, + "content": [] + } + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 10, + "output_tokens": 5 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + ChatResponse response = await chatClient.GetResponseAsync("Run failing code"); + + CodeInterpreterToolResultContent codeResult = + Assert.IsType(response.Messages[0].Contents[0]); + Assert.NotNull(codeResult.Outputs); + Assert.Single(codeResult.Outputs); + + ErrorContent errorOutput = Assert.IsType(codeResult.Outputs[0]); + Assert.Equal("Division by zero error", errorOutput.Message); + Assert.Equal("1", errorOutput.ErrorCode); + } + + [Fact] + public async Task GetResponseAsync_CodeExecutionResult_WithFileOutputs() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Create file" + }] + }] + } + """, + actualResponse: """ + { + "id": "msg_code_files_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "code_execution_tool_result", + "tool_use_id": "code_exec_3", + "content": { + "type": "code_execution_result", + "stdout": "File created", + "stderr": "", + "return_code": 0, + "content": [{ + "type": "code_execution_output", + "file_id": "file_output_123" + }, { + "type": "code_execution_output", + "file_id": "file_output_456" + }] + } + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 10, + "output_tokens": 5 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + ChatResponse response = await chatClient.GetResponseAsync("Create file"); + + CodeInterpreterToolResultContent codeResult = + Assert.IsType(response.Messages[0].Contents[0]); + Assert.NotNull(codeResult.Outputs); + Assert.Equal(3, codeResult.Outputs.Count); + + TextContent textOutput = Assert.IsType(codeResult.Outputs[0]); + Assert.Equal("File created", textOutput.Text); + + HostedFileContent fileOutput1 = Assert.IsType(codeResult.Outputs[1]); + Assert.Equal("file_output_123", fileOutput1.FileId); + + HostedFileContent fileOutput2 = Assert.IsType(codeResult.Outputs[2]); + Assert.Equal("file_output_456", fileOutput2.FileId); + } + + [Fact] + public async Task GetResponseAsync_BashCodeExecutionResult_WithStdout() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Run bash" + }] + }] + } + """, + actualResponse: """ + { + "id": "msg_bash_stdout_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "bash_code_execution_tool_result", + "tool_use_id": "bash_exec_1", + "content": { + "type": "bash_code_execution_result", + "stdout": "Hello from bash\n5\n", + "stderr": "", + "return_code": 0, + "content": [] + } + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 10, + "output_tokens": 5 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + ChatResponse response = await chatClient.GetResponseAsync("Run bash"); + + CodeInterpreterToolResultContent codeResult = + Assert.IsType(response.Messages[0].Contents[0]); + Assert.NotNull(codeResult); + Assert.Equal("bash_exec_1", codeResult.CallId); + Assert.NotNull(codeResult.Outputs); + Assert.Single(codeResult.Outputs); + + TextContent textOutput = Assert.IsType(codeResult.Outputs[0]); + Assert.Equal("Hello from bash\n5\n", textOutput.Text); + } + + [Fact] + public async Task GetResponseAsync_BashCodeExecutionResult_WithStderrAndNonZeroReturnCode() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Run failing bash" + }] + }] + } + """, + actualResponse: """ + { + "id": "msg_bash_stderr_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "bash_code_execution_tool_result", + "tool_use_id": "bash_exec_2", + "content": { + "type": "bash_code_execution_result", + "stdout": "", + "stderr": "bash: command not found: nonexistent", + "return_code": 127, + "content": [] + } + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 10, + "output_tokens": 5 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + ChatResponse response = await chatClient.GetResponseAsync("Run failing bash"); + + CodeInterpreterToolResultContent codeResult = + Assert.IsType(response.Messages[0].Contents[0]); + Assert.NotNull(codeResult.Outputs); + Assert.Single(codeResult.Outputs); + + ErrorContent errorOutput = Assert.IsType(codeResult.Outputs[0]); + Assert.Equal("bash: command not found: nonexistent", errorOutput.Message); + Assert.Equal("127", errorOutput.ErrorCode); + } + + [Fact] + public async Task GetResponseAsync_BashCodeExecutionResult_WithFileOutputs() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Create files with bash" + }] + }] + } + """, + actualResponse: """ + { + "id": "msg_bash_files_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "bash_code_execution_tool_result", + "tool_use_id": "bash_exec_3", + "content": { + "type": "bash_code_execution_result", + "stdout": "Files created successfully", + "stderr": "", + "return_code": 0, + "content": [{ + "type": "bash_code_execution_output", + "file_id": "file_bash_123" + }, { + "type": "bash_code_execution_output", + "file_id": "file_bash_456" + }] + } + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 10, + "output_tokens": 5 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + ChatResponse response = await chatClient.GetResponseAsync("Create files with bash"); + + CodeInterpreterToolResultContent codeResult = + Assert.IsType(response.Messages[0].Contents[0]); + Assert.NotNull(codeResult.Outputs); + Assert.Equal(3, codeResult.Outputs.Count); + + TextContent textOutput = Assert.IsType(codeResult.Outputs[0]); + Assert.Equal("Files created successfully", textOutput.Text); + + HostedFileContent fileOutput1 = Assert.IsType(codeResult.Outputs[1]); + Assert.Equal("file_bash_123", fileOutput1.FileId); + + HostedFileContent fileOutput2 = Assert.IsType(codeResult.Outputs[2]); + Assert.Equal("file_bash_456", fileOutput2.FileId); + } + + [Fact] + public async Task GetResponseAsync_WithHostedTools_AddsBetaHeaders() + { + IEnumerable? capturedBetaHeaders = null; + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Use both tools" + }] + }], + "tools": [{ + "type": "code_execution_20250825", + "name": "code_execution" + }], + "mcp_servers": [{ + "name": "mcp", + "type": "url", + "url": "https://mcp.example.com/server" + }] + } + """, + actualResponse: """ + { + "id": "msg_both_beta_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "text", + "text": "I have access to both tools." + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 25, + "output_tokens": 10 + } + } + """ + ) + { + OnRequestHeaders = headers => + headers.TryGetValues("anthropic-beta", out capturedBetaHeaders), + }; + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + + ChatOptions options = new() + { + Tools = + [ + new HostedCodeInterpreterTool(), + new HostedMcpServerTool("my-mcp-server", new Uri("https://mcp.example.com/server")), + ], + }; + + ChatResponse response = await chatClient.GetResponseAsync("Use both tools", options); + Assert.NotNull(response); + Assert.NotNull(capturedBetaHeaders); + Assert.Contains("code-execution-2025-08-25", capturedBetaHeaders); + Assert.Contains("mcp-client-2025-11-20", capturedBetaHeaders); + } + + [Fact] + public async Task GetResponseAsync_WithHostedToolsAndExistingBetas_PreservesAndDeduplicatesBetas() + { + IEnumerable? capturedBetaHeaders = null; + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Test" + }] + }], + "tools": [{ + "type": "code_execution_20250825", + "name": "code_execution" + }], + "mcp_servers": [{ + "name": "mcp", + "type": "url", + "url": "https://mcp.example.com/server" + }] + } + """, + actualResponse: """ + { + "id": "msg_preserve_beta_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "text", + "text": "Response" + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 10, + "output_tokens": 5 + } + } + """ + ) + { + OnRequestHeaders = headers => + headers.TryGetValues("anthropic-beta", out capturedBetaHeaders), + }; + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + + ChatOptions options = new() + { + RawRepresentationFactory = _ => new MessageCreateParams() + { + MaxTokens = 1024, + Model = "claude-haiku-4-5", + Messages = [], + Betas = ["custom-beta-feature", "code-execution-2025-08-25"], + }, + Tools = + [ + new HostedCodeInterpreterTool(), + new HostedMcpServerTool("my-mcp-server", new Uri("https://mcp.example.com/server")), + ], + }; + + ChatResponse response = await chatClient.GetResponseAsync("Test", options); + Assert.NotNull(response); + Assert.NotNull(capturedBetaHeaders); + Assert.Equal(3, capturedBetaHeaders.Count()); + Assert.Contains("custom-beta-feature", capturedBetaHeaders); + Assert.Contains("code-execution-2025-08-25", capturedBetaHeaders); + Assert.Contains("mcp-client-2025-11-20", capturedBetaHeaders); + } } diff --git a/src/Anthropic.Tests/AnthropicClientExtensionsTests.cs b/src/Anthropic.Tests/AnthropicClientExtensionsTests.cs index 02ff03ef..3443c7d8 100644 --- a/src/Anthropic.Tests/AnthropicClientExtensionsTests.cs +++ b/src/Anthropic.Tests/AnthropicClientExtensionsTests.cs @@ -1,4 +1,7 @@ using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; using System.Threading.Tasks; using Anthropic; using Anthropic.Models.Messages; @@ -222,4 +225,241 @@ public async Task GetResponseAsync_WithToolUnionAsAITool_FlowsThroughToRequest() ChatResponse response = await chatClient.GetResponseAsync("Search the web", options); Assert.NotNull(response); } + + [Fact] + public void AsAITool_GetService_ReturnsToolUnion() + { + ToolUnion toolUnion = new WebSearchTool20250305() { AllowedDomains = ["example.com"] }; + AITool aiTool = toolUnion.AsAITool(); + + Assert.Same(toolUnion, aiTool.GetService()); + + Assert.Null(aiTool.GetService("key")); + Assert.Null(aiTool.GetService()); + + Assert.NotNull(aiTool.Name); + Assert.Contains(nameof(WebSearchTool20250305), aiTool.Name); + } + + [Fact] + public void AsAITool_GetService_ThrowsOnNullServiceType() + { + AITool aiTool = ( + (ToolUnion)new WebSearchTool20250305() { AllowedDomains = ["example.com"] } + ).AsAITool(); + Assert.Throws(() => aiTool.GetService(null!, null)); + } + + [Fact] + public async Task GetResponseAsync_WithRawRepresentationFactory() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 2048, + "model": "claude-haiku-4-5", + "messages": [ + { + "role": "user", + "content": [{ + "type": "text", + "text": "Preconfigured message" + }] + }, + { + "role": "user", + "content": [{ + "type": "text", + "text": "New message" + }] + } + ] + } + """, + actualResponse: """ + { + "id": "msg_factory_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "text", + "text": "Response" + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 20, + "output_tokens": 5 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + + ChatOptions options = new() + { + RawRepresentationFactory = _ => new MessageCreateParams() + { + MaxTokens = 2048, + Model = "claude-haiku-4-5", + Messages = + [ + new MessageParam() + { + Role = Role.User, + Content = new MessageParamContent( + [new TextBlockParam() { Text = "Preconfigured message" }] + ), + }, + ], + }, + }; + + ChatResponse response = await chatClient.GetResponseAsync("New message", options); + Assert.NotNull(response); + } + + [Fact] + public async Task GetResponseAsync_WithRawRepresentationFactory_SystemMessagesMerged() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Test" + }] + }], + "system": [ + { + "type": "text", + "text": "Existing system message" + }, + { + "type": "text", + "text": "New system message" + } + ] + } + """, + actualResponse: """ + { + "id": "msg_sys_merge_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "text", + "text": "Response" + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 15, + "output_tokens": 5 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + + ChatOptions options = new() + { + RawRepresentationFactory = _ => new MessageCreateParams() + { + MaxTokens = 1024, + Model = "claude-haiku-4-5", + Messages = [], + System = "Existing system message", + }, + }; + + ChatResponse response = await chatClient.GetResponseAsync( + [ + new ChatMessage(ChatRole.System, "New system message"), + new ChatMessage(ChatRole.User, "Test"), + ], + options + ); + Assert.NotNull(response); + } + + [Fact] + public async Task GetResponseAsync_WithRawRepresentationFactory_SystemMessagesListMerged() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Test" + }] + }], + "system": [ + { + "type": "text", + "text": "First" + }, + { + "type": "text", + "text": "Second" + }, + { + "type": "text", + "text": "Third" + } + ] + } + """, + actualResponse: """ + { + "id": "msg_sys_list_merge_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "text", + "text": "Response" + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 15, + "output_tokens": 5 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + + ChatOptions options = new() + { + RawRepresentationFactory = _ => new MessageCreateParams() + { + MaxTokens = 1024, + Model = "claude-haiku-4-5", + Messages = [], + System = new System.Collections.Generic.List + { + new() { Text = "First" }, + new() { Text = "Second" }, + }, + }, + }; + + ChatResponse response = await chatClient.GetResponseAsync( + [new ChatMessage(ChatRole.System, "Third"), new ChatMessage(ChatRole.User, "Test")], + options + ); + Assert.NotNull(response); + } } diff --git a/src/Anthropic.Tests/AnthropicClientExtensionsTestsBase.cs b/src/Anthropic.Tests/AnthropicClientExtensionsTestsBase.cs index d5e90f27..fc903291 100644 --- a/src/Anthropic.Tests/AnthropicClientExtensionsTestsBase.cs +++ b/src/Anthropic.Tests/AnthropicClientExtensionsTestsBase.cs @@ -2,6 +2,7 @@ using System.Collections.Generic; using System.Linq; using System.Net.Http; +using System.Net.Http.Headers; using System.Text; using System.Text.Json; using System.Text.Json.Nodes; @@ -54,6 +55,51 @@ public void AsIChatClient_GetService_ReturnsKnownTypes(string? defaultModelId) Assert.Null(chatClient.GetService()); } + [Fact] + public void AsIChatClient_GetService_ThrowsOnNullServiceType() + { + IChatClient chatClient = CreateChatClient( + new VerbatimHttpHandler("", ""), + "claude-haiku-4-5" + ); + Assert.Throws(() => chatClient.GetService(null!, null)); + } + + [Fact] + public void AsIChatClient_GetService_ReturnsNullWithNonNullServiceKey() + { + IChatClient chatClient = CreateChatClient( + new VerbatimHttpHandler("", ""), + "claude-haiku-4-5" + ); + Assert.Null(chatClient.GetService(typeof(string), "someKey")); + } + + [Fact] + public void AsIChatClient_GetService_ReturnsMetadata() + { + AnthropicClient client = new() { APIKey = "test-key" }; + IChatClient chatClient = CreateChatClient(client, "claude-haiku-4-5"); + + var metadata = chatClient.GetService(); + + Assert.NotNull(metadata); + Assert.Equal("anthropic", metadata.ProviderName); + Assert.Equal("claude-haiku-4-5", metadata.DefaultModelId); + } + + [Fact] + public void AsIChatClient_GetService_ReturnsSelf() + { + AnthropicClient client = new() { APIKey = "test-key" }; + IChatClient chatClient = CreateChatClient(client, "claude-haiku-4-5"); + + var self = chatClient.GetService(); + + Assert.NotNull(self); + Assert.Same(chatClient, self); + } + [Fact] public void IChatClient_Dispose_Nop() { @@ -635,28 +681,154 @@ public async Task GetStreamingResponseAsync_BasicTextCompletion() } [Fact] - public void AsIChatClient_GetService_ReturnsMetadata() + public async Task GetResponseAsync_WithTextDataContent() { - AnthropicClient client = new() { APIKey = "test-key" }; - IChatClient chatClient = CreateChatClient(client, "claude-haiku-4-5"); + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "document", + "source": { + "type": "text", + "media_type": "text/plain", + "data": "Sample text content" + } + }] + }] + } + """, + actualResponse: """ + { + "id": "msg_text_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "text", + "text": "I read the text." + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 15, + "output_tokens": 5 + } + } + """ + ); - var metadata = chatClient.GetService(); + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); - Assert.NotNull(metadata); - Assert.Equal("anthropic", metadata.ProviderName); - Assert.Equal("claude-haiku-4-5", metadata.DefaultModelId); + var dataContent = new DataContent( + Encoding.UTF8.GetBytes("Sample text content"), + "text/plain" + ); + + ChatResponse response = await chatClient.GetResponseAsync( + [new ChatMessage(ChatRole.User, [dataContent])] + ); + Assert.NotNull(response); } [Fact] - public void AsIChatClient_GetService_ReturnsSelf() + public async Task GetResponseAsync_WithImageUriContent() { - AnthropicClient client = new() { APIKey = "test-key" }; - IChatClient chatClient = CreateChatClient(client, "claude-haiku-4-5"); + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "image", + "source": { + "type": "url", + "url": "https://example.com/image.jpg" + } + }] + }] + } + """, + actualResponse: """ + { + "id": "msg_img_uri_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "text", + "text": "I see the image." + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 20, + "output_tokens": 6 + } + } + """ + ); - var self = chatClient.GetService(); + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); - Assert.NotNull(self); - Assert.Same(chatClient, self); + var imageUri = new UriContent(new Uri("https://example.com/image.jpg"), "image/jpeg"); + + ChatResponse response = await chatClient.GetResponseAsync( + [new ChatMessage(ChatRole.User, [imageUri])] + ); + Assert.NotNull(response); + } + + [Fact] + public async Task GetResponseAsync_WithPdfUriContent() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "document", + "source": { + "type": "url", + "url": "https://example.com/document.pdf" + } + }] + }] + } + """, + actualResponse: """ + { + "id": "msg_pdf_01", + "type": "message", + "role": "assistant", + "model": "claude-haiku-4-5", + "content": [{ + "type": "text", + "text": "I analyzed the PDF." + }], + "stop_reason": "end_turn", + "usage": { + "input_tokens": 20, + "output_tokens": 6 + } + } + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + + var pdfUri = new UriContent(new Uri("https://example.com/document.pdf"), "application/pdf"); + + ChatResponse response = await chatClient.GetResponseAsync( + [new ChatMessage(ChatRole.User, [pdfUri])] + ); + Assert.NotNull(response); } [Fact] @@ -1894,6 +2066,11 @@ public async Task GetStreamingResponseAsync_WithToolCallInputDelta() .FirstOrDefault(); Assert.NotNull(functionCall); Assert.Equal("test_tool", functionCall.Name); + + // Verify arguments were properly accumulated from multiple delta events + Assert.NotNull(functionCall.Arguments); + Assert.True(functionCall.Arguments.ContainsKey("arg")); + Assert.Equal("value", functionCall.Arguments["arg"]?.ToString()); } [Fact] @@ -1958,6 +2135,317 @@ var update in chatClient.GetStreamingResponseAsync("Call parameterless tool") Assert.True(functionCall.Arguments == null || functionCall.Arguments.Count == 0); } + [Fact] + public async Task GetStreamingResponseAsync_WithMultipleToolCalls_DoesNotDuplicateFunctionCalls() + { + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Call multiple tools" + }] + }], + "stream": true + } + """, + actualResponse: """ + event: message_start + data: {"type":"message_start","message":{"id":"msg_multi_tool_01","type":"message","role":"assistant","model":"claude-haiku-4-5","content":[],"stop_reason":null,"stop_sequence":null,"usage":{"input_tokens":10,"output_tokens":0}}} + + event: content_block_start + data: {"type":"content_block_start","index":0,"content_block":{"type":"tool_use","id":"toolu_1","name":"tool_a","input":{}}} + + event: content_block_delta + data: {"type":"content_block_delta","index":0,"delta":{"type":"input_json_delta","partial_json":"{\"arg\":\"a\"}"}} + + event: content_block_stop + data: {"type":"content_block_stop","index":0} + + event: content_block_start + data: {"type":"content_block_start","index":1,"content_block":{"type":"tool_use","id":"toolu_2","name":"tool_b","input":{}}} + + event: content_block_delta + data: {"type":"content_block_delta","index":1,"delta":{"type":"input_json_delta","partial_json":"{\"arg\":\"b\"}"}} + + event: content_block_stop + data: {"type":"content_block_stop","index":1} + + event: content_block_start + data: {"type":"content_block_start","index":2,"content_block":{"type":"tool_use","id":"toolu_3","name":"tool_c","input":{}}} + + event: content_block_delta + data: {"type":"content_block_delta","index":2,"delta":{"type":"input_json_delta","partial_json":"{\"arg\":\"c\"}"}} + + event: content_block_stop + data: {"type":"content_block_stop","index":2} + + event: message_delta + data: {"type":"message_delta","delta":{"stop_reason":"tool_use","stop_sequence":null},"usage":{"output_tokens":15}} + + event: message_stop + data: {"type":"message_stop"} + + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + + List updates = []; + await foreach (var update in chatClient.GetStreamingResponseAsync("Call multiple tools")) + { + updates.Add(update); + } + + var allFunctionCalls = updates + .SelectMany(u => u.Contents.OfType()) + .ToList(); + + Assert.Equal(3, allFunctionCalls.Count); + + var fccA = allFunctionCalls.First(fc => fc.Name == "tool_a"); + Assert.Equal("toolu_1", fccA.CallId); + Assert.Equal("a", fccA.Arguments?["arg"]?.ToString()); + + var fccB = allFunctionCalls.First(fc => fc.Name == "tool_b"); + Assert.Equal("toolu_2", fccB.CallId); + Assert.Equal("b", fccB.Arguments?["arg"]?.ToString()); + + var fccC = allFunctionCalls.First(fc => fc.Name == "tool_c"); + Assert.Equal("toolu_3", fccC.CallId); + Assert.Equal("c", fccC.Arguments?["arg"]?.ToString()); + } + + [Fact] + public async Task GetStreamingResponseAsync_WithManyToolCallsAndFragmentedArguments() + { + // Build a streaming response with 5 tool calls, each with arguments spread across many small delta events + var responseBuilder = new StringBuilder(); + responseBuilder.AppendLine( + """ + event: message_start + data: {"type":"message_start","message":{"id":"msg_many_tools_01","type":"message","role":"assistant","model":"claude-haiku-4-5","content":[],"stop_reason":null,"stop_sequence":null,"usage":{"input_tokens":10,"output_tokens":0}}} + + """ + ); + + // Create 5 tool calls, each with complex arguments spread over multiple deltas + for (int toolIndex = 0; toolIndex < 5; toolIndex++) + { + char toolLetter = (char)('a' + toolIndex); + string toolId = $"toolu_{toolIndex + 1}"; + string toolName = $"tool_{toolLetter}"; + + // Start the tool use block + responseBuilder.AppendLine( + $"event: content_block_start\n" + + $"data: {{\"type\":\"content_block_start\",\"index\":{toolIndex},\"content_block\":{{\"type\":\"tool_use\",\"id\":\"{toolId}\",\"name\":\"{toolName}\",\"input\":{{}}}}}}\n" + ); + + // Build the JSON argument piece by piece + string fullJson = + $"{{\"name\":\"tool_{toolLetter}_value\",\"count\":{toolIndex + 1},\"description\":\"This is tool {toolLetter} with a longer description to test accumulation\"}}"; + + // Split the JSON into small chunks (3 characters each) to simulate realistic streaming + int chunkSize = 3; + for (int i = 0; i < fullJson.Length; i += chunkSize) + { + string chunk = fullJson.Substring(i, Math.Min(chunkSize, fullJson.Length - i)); + // Escape the chunk for JSON embedding + string escapedChunk = chunk.Replace("\\", "\\\\").Replace("\"", "\\\""); + responseBuilder.AppendLine( + $"event: content_block_delta\n" + + $"data: {{\"type\":\"content_block_delta\",\"index\":{toolIndex},\"delta\":{{\"type\":\"input_json_delta\",\"partial_json\":\"{escapedChunk}\"}}}}\n" + ); + } + + // Stop the content block + responseBuilder.AppendLine( + $"event: content_block_stop\n" + + $"data: {{\"type\":\"content_block_stop\",\"index\":{toolIndex}}}\n" + ); + } + + // End the message + responseBuilder.AppendLine( + """ + event: message_delta + data: {"type":"message_delta","delta":{"stop_reason":"tool_use","stop_sequence":null},"usage":{"output_tokens":50}} + + event: message_stop + data: {"type":"message_stop"} + + """ + ); + + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Call many tools" + }] + }], + "stream": true + } + """, + actualResponse: responseBuilder.ToString() + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + + List updates = []; + await foreach (var update in chatClient.GetStreamingResponseAsync("Call many tools")) + { + updates.Add(update); + } + + var allFunctionCalls = updates + .SelectMany(u => u.Contents.OfType()) + .ToList(); + + Assert.Equal(5, allFunctionCalls.Count); + for (int i = 0; i < 5; i++) + { + string expectedCallId = $"toolu_{i + 1}"; + string expectedName = $"tool_{(char)('a' + i)}"; + string expectedNameValue = $"tool_{(char)('a' + i)}_value"; + int expectedCount = i + 1; + + var functionCall = allFunctionCalls.SingleOrDefault(fc => fc.CallId == expectedCallId); + Assert.NotNull(functionCall); + Assert.Equal(expectedName, functionCall.Name); + + Assert.NotNull(functionCall.Arguments); + Assert.Equal(expectedNameValue, functionCall.Arguments["name"]?.ToString()); + Assert.Equal(expectedCount.ToString(), functionCall.Arguments["count"]?.ToString()); + Assert.Contains( + $"This is tool {(char)('a' + i)}", + functionCall.Arguments["description"]?.ToString() + ); + } + } + + [Fact] + public async Task GetStreamingResponseAsync_WithInterleavedToolCallDeltas() + { + // This test simulates a scenario where multiple tool calls are being streamed + // with their argument deltas interleaved (receiving parts of all tools before any completes) + VerbatimHttpHandler handler = new( + expectedRequest: """ + { + "max_tokens": 1024, + "model": "claude-haiku-4-5", + "messages": [{ + "role": "user", + "content": [{ + "type": "text", + "text": "Call interleaved tools" + }] + }], + "stream": true + } + """, + actualResponse: """ + event: message_start + data: {"type":"message_start","message":{"id":"msg_interleaved_01","type":"message","role":"assistant","model":"claude-haiku-4-5","content":[],"stop_reason":null,"stop_sequence":null,"usage":{"input_tokens":10,"output_tokens":0}}} + + event: content_block_start + data: {"type":"content_block_start","index":0,"content_block":{"type":"tool_use","id":"toolu_alpha","name":"tool_alpha","input":{}}} + + event: content_block_start + data: {"type":"content_block_start","index":1,"content_block":{"type":"tool_use","id":"toolu_beta","name":"tool_beta","input":{}}} + + event: content_block_start + data: {"type":"content_block_start","index":2,"content_block":{"type":"tool_use","id":"toolu_gamma","name":"tool_gamma","input":{}}} + + event: content_block_delta + data: {"type":"content_block_delta","index":0,"delta":{"type":"input_json_delta","partial_json":"{\"city\":"}} + + event: content_block_delta + data: {"type":"content_block_delta","index":1,"delta":{"type":"input_json_delta","partial_json":"{\"query\":"}} + + event: content_block_delta + data: {"type":"content_block_delta","index":2,"delta":{"type":"input_json_delta","partial_json":"{\"id\":"}} + + event: content_block_delta + data: {"type":"content_block_delta","index":0,"delta":{"type":"input_json_delta","partial_json":"\"San Fran"}} + + event: content_block_delta + data: {"type":"content_block_delta","index":1,"delta":{"type":"input_json_delta","partial_json":"\"weather "}} + + event: content_block_delta + data: {"type":"content_block_delta","index":2,"delta":{"type":"input_json_delta","partial_json":"123,\"act"}} + + event: content_block_delta + data: {"type":"content_block_delta","index":0,"delta":{"type":"input_json_delta","partial_json":"cisco\"}"}} + + event: content_block_delta + data: {"type":"content_block_delta","index":1,"delta":{"type":"input_json_delta","partial_json":"forecast\"}"}} + + event: content_block_delta + data: {"type":"content_block_delta","index":2,"delta":{"type":"input_json_delta","partial_json":"ive\":true}"}} + + event: content_block_stop + data: {"type":"content_block_stop","index":0} + + event: content_block_stop + data: {"type":"content_block_stop","index":1} + + event: content_block_stop + data: {"type":"content_block_stop","index":2} + + event: message_delta + data: {"type":"message_delta","delta":{"stop_reason":"tool_use","stop_sequence":null},"usage":{"output_tokens":25}} + + event: message_stop + data: {"type":"message_stop"} + + """ + ); + + IChatClient chatClient = CreateChatClient(handler, "claude-haiku-4-5"); + + List updates = []; + await foreach (var update in chatClient.GetStreamingResponseAsync("Call interleaved tools")) + { + updates.Add(update); + } + + var allFunctionCalls = updates + .SelectMany(u => u.Contents.OfType()) + .ToList(); + + Assert.Equal(3, allFunctionCalls.Count); + + var alphaCall = allFunctionCalls.SingleOrDefault(fc => fc.CallId == "toolu_alpha"); + Assert.NotNull(alphaCall); + Assert.Equal("tool_alpha", alphaCall.Name); + Assert.NotNull(alphaCall.Arguments); + Assert.Equal("San Francisco", alphaCall.Arguments["city"]?.ToString()); + + var betaCall = allFunctionCalls.SingleOrDefault(fc => fc.CallId == "toolu_beta"); + Assert.NotNull(betaCall); + Assert.Equal("tool_beta", betaCall.Name); + Assert.NotNull(betaCall.Arguments); + Assert.Equal("weather forecast", betaCall.Arguments["query"]?.ToString()); + + var gammaCall = allFunctionCalls.SingleOrDefault(fc => fc.CallId == "toolu_gamma"); + Assert.NotNull(gammaCall); + Assert.Equal("tool_gamma", gammaCall.Name); + Assert.NotNull(gammaCall.Arguments); + Assert.Equal("123", gammaCall.Arguments["id"]?.ToString()); + Assert.Equal("True", gammaCall.Arguments["active"]?.ToString()); + } + [Fact] public async Task GetResponseAsync_WithAdditionalUsageCounts() { @@ -2983,38 +3471,6 @@ var update in chatClient.GetStreamingResponseAsync("Test multiple message starts Assert.Equal(2, usageContent.Details.OutputTokenCount); } - protected sealed class VerbatimHttpHandler(string expectedRequest, string actualResponse) - : HttpMessageHandler - { - protected override async Task SendAsync( - HttpRequestMessage request, - CancellationToken cancellationToken - ) - { - if (!string.IsNullOrEmpty(expectedRequest)) - { - Assert.NotNull(request.Content); - string actualRequest = await request.Content.ReadAsStringAsync( -#if NET - cancellationToken -#endif - ); - Assert.True( - JsonNode.DeepEquals( - JsonNode.Parse(expectedRequest), - JsonNode.Parse(actualRequest) - ), - $"Expected:\n{expectedRequest}\nActual:\n{actualRequest}" - ); - } - - return new() - { - Content = new StringContent(actualResponse, Encoding.UTF8, "application/json"), - }; - } - } - [Fact] public async Task GetResponseAsync_FunctionResult_WithSingleTextContent() { @@ -3833,4 +4289,40 @@ public async Task GetResponseAsync_WithFunctionResultContent_UriContent_PDF() ChatResponse response = await chatClient.GetResponseAsync(messages); Assert.NotNull(response); } + + protected sealed class VerbatimHttpHandler(string expectedRequest, string actualResponse) + : HttpMessageHandler + { + public Action? OnRequestHeaders { get; set; } + + protected override async Task SendAsync( + HttpRequestMessage request, + CancellationToken cancellationToken + ) + { + OnRequestHeaders?.Invoke(request.Headers); + + if (!string.IsNullOrEmpty(expectedRequest)) + { + Assert.NotNull(request.Content); + string actualRequest = await request.Content.ReadAsStringAsync( +#if NET + cancellationToken +#endif + ); + Assert.True( + JsonNode.DeepEquals( + JsonNode.Parse(expectedRequest), + JsonNode.Parse(actualRequest) + ), + $"Expected:\n{expectedRequest}\nActual:\n{actualRequest}" + ); + } + + return new() + { + Content = new StringContent(actualResponse, Encoding.UTF8, "application/json"), + }; + } + } } diff --git a/src/Anthropic.Tests/AnthropicTestClients.cs b/src/Anthropic.Tests/AnthropicTestClients.cs index 7172c476..337cd252 100644 --- a/src/Anthropic.Tests/AnthropicTestClients.cs +++ b/src/Anthropic.Tests/AnthropicTestClients.cs @@ -9,6 +9,11 @@ namespace Anthropic.Tests; public class AnthropicTestClientsAttribute : DataAttribute { + public static string DataServiceUrl { get; } = + Environment.GetEnvironmentVariable("TEST_API_BASE_URL") ?? "http://localhost:4010"; + public static string ApiKey { get; } = "YourApiKeyHere"; + public static string Resource { get; } = "YourRegionOrResourceHere"; + public AnthropicTestClientsAttribute(TestSupportTypes testSupportTypes = TestSupportTypes.All) { TestSupportTypes = testSupportTypes; @@ -18,17 +23,12 @@ public AnthropicTestClientsAttribute(TestSupportTypes testSupportTypes = TestSup public override IEnumerable GetData(MethodInfo testMethod) { - var dataServiceUrl = - Environment.GetEnvironmentVariable("TEST_API_BASE_URL") ?? "http://localhost:4010"; - string apiKey = "YourApiKeyHere"; - var resource = "YourRegionOrResourceHere"; - var testData = testMethod.GetCustomAttributes().ToArray(); if (TestSupportTypes.HasFlag(TestSupportTypes.Anthropic)) { yield return [ - new AnthropicClient() { BaseUrl = new Uri(dataServiceUrl), APIKey = apiKey }, + new AnthropicClient() { BaseUrl = new Uri(DataServiceUrl), APIKey = ApiKey }, .. testData .Where(e => e.TestSupport.HasFlag(TestSupportTypes.Anthropic)) .Select(f => f.TestData) @@ -39,9 +39,9 @@ .. testData { yield return [ - new AnthropicFoundryClient(new AnthropicFoundryApiKeyCredentials(apiKey, resource!)) + new AnthropicFoundryClient(new AnthropicFoundryApiKeyCredentials(ApiKey, Resource!)) { - BaseUrl = new Uri(dataServiceUrl), + BaseUrl = new Uri(DataServiceUrl), }, .. testData .Where(e => e.TestSupport.HasFlag(TestSupportTypes.Foundry)) diff --git a/src/Anthropic.Tests/Core/FreezableDictionaryTest.cs b/src/Anthropic.Tests/Core/FreezableDictionaryTest.cs new file mode 100644 index 00000000..86fd076b --- /dev/null +++ b/src/Anthropic.Tests/Core/FreezableDictionaryTest.cs @@ -0,0 +1,43 @@ +using System; +using System.Collections.Generic; +using Anthropic.Core; + +namespace Anthropic.Tests.Core; + +public class FreezableDictionaryTest : TestBase +{ + [Fact] + public void Unfrozen_Works() + { + var freezable = new FreezableDictionary(); + Assert.Throws(() => freezable["foo"]); + freezable["foo"] = "bar"; + Assert.Equal("bar", freezable["foo"]); + + // overwriting key + freezable["foo"] = "baz"; + Assert.Equal("baz", freezable["foo"]); + + // inserting new key + freezable["bar"] = "foo"; + Assert.Equal("foo", freezable["bar"]); + + Assert.Equal("baz", freezable["foo"]); + } + + [Fact] + public void Frozen_Works() + { + var freezable = new FreezableDictionary() { ["foo"] = "bar" }; + Assert.Equal("bar", freezable.Freeze()["foo"]); + Assert.Equal("bar", freezable["foo"]); + Assert.Throws(() => freezable["bar"]); + Assert.Throws(() => freezable.Freeze()["bar"]); + + // overwriting key + Assert.Throws(() => freezable["foo"] = "baz"); + + // inserting new key + Assert.Throws(() => freezable["baz"] = "buzz"); + } +} diff --git a/src/Anthropic.Tests/Core/ModelBaseTest.cs b/src/Anthropic.Tests/Core/ModelBaseTest.cs new file mode 100644 index 00000000..ac5613df --- /dev/null +++ b/src/Anthropic.Tests/Core/ModelBaseTest.cs @@ -0,0 +1,197 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; + +namespace Anthropic.Tests.Core; + +public class ModelBaseTest +{ + [Fact] + public void GetNotNullClass_WhenPresent_Works() + { + var dictionary = new Dictionary(); + ModelBase.Set(dictionary, "key", "value"); + + var value = ModelBase.GetNotNullClass(dictionary, "key"); + + Assert.Equal("value", value); + } + + [Fact] + public void GetNotNullClass_WhenAbsent_Throws() + { + var dictionary = new Dictionary(); + + var exception = Assert.Throws(() => + ModelBase.GetNotNullClass(dictionary, "key") + ); + + Assert.Equal("'key' cannot be absent", exception.Message); + } + + [Fact] + public void GetNotNullClass_WhenNull_Throws() + { + var dictionary = new Dictionary(); + ModelBase.Set(dictionary, "key", null); + + var exception = Assert.Throws(() => + ModelBase.GetNotNullClass(dictionary, "key") + ); + + Assert.Equal("'key' cannot be null", exception.Message); + } + + [Fact] + public void GetNotNullClass_WhenMismatchedType_Throws() + { + var dictionary = new Dictionary(); + ModelBase.Set(dictionary, "key", 42); + + var exception = Assert.Throws(() => + ModelBase.GetNotNullClass(dictionary, "key") + ); + + Assert.Equal("'key' must be of type System.String", exception.Message); + } + + [Fact] + public void GetNotNullStruct_WhenPresent_Works() + { + var dictionary = new Dictionary(); + ModelBase.Set(dictionary, "key", 42); + + var value = ModelBase.GetNotNullStruct(dictionary, "key"); + + Assert.Equal(42, value); + } + + [Fact] + public void GetNotNullStruct_WhenAbsent_Throws() + { + var dictionary = new Dictionary(); + + var exception = Assert.Throws(() => + ModelBase.GetNotNullStruct(dictionary, "key") + ); + + Assert.Equal("'key' cannot be absent", exception.Message); + } + + [Fact] + public void GetNotNullStruct_WhenNull_Throws() + { + var dictionary = new Dictionary(); + ModelBase.Set(dictionary, "key", null); + + var exception = Assert.Throws(() => + ModelBase.GetNotNullStruct(dictionary, "key") + ); + + Assert.Equal("'key' cannot be null", exception.Message); + } + + [Fact] + public void GetNotNullStruct_WhenMismatchedType_Throws() + { + var dictionary = new Dictionary(); + ModelBase.Set(dictionary, "key", "value"); + + var exception = Assert.Throws(() => + ModelBase.GetNotNullStruct(dictionary, "key") + ); + + Assert.Equal("'key' must be of type System.Int32", exception.Message); + } + + [Fact] + public void GetNullableClass_WhenPresent_Works() + { + var dictionary = new Dictionary(); + ModelBase.Set(dictionary, "key", "value"); + + var value = ModelBase.GetNullableClass(dictionary, "key"); + + Assert.Equal("value", value); + } + + [Fact] + public void GetNullableClass_WhenAbsent_ReturnsNull() + { + var dictionary = new Dictionary(); + + var value = ModelBase.GetNullableClass(dictionary, "key"); + + Assert.Null(value); + } + + [Fact] + public void GetNullableClass_WhenNull_ReturnsNull() + { + var dictionary = new Dictionary(); + ModelBase.Set(dictionary, "key", null); + + var value = ModelBase.GetNullableClass(dictionary, "key"); + + Assert.Null(value); + } + + [Fact] + public void GetNullableClass_WhenMismatchedType_Throws() + { + var dictionary = new Dictionary(); + ModelBase.Set(dictionary, "key", 42); + + var exception = Assert.Throws(() => + ModelBase.GetNullableClass(dictionary, "key") + ); + + Assert.Equal("'key' must be of type System.String", exception.Message); + } + + [Fact] + public void GetNullableStruct_WhenPresent_Works() + { + var dictionary = new Dictionary(); + ModelBase.Set(dictionary, "key", 42); + + var value = ModelBase.GetNullableStruct(dictionary, "key"); + + Assert.Equal(42, value); + } + + [Fact] + public void GetNullableStruct_WhenAbsent_ReturnsNull() + { + var dictionary = new Dictionary(); + + var value = ModelBase.GetNullableStruct(dictionary, "key"); + + Assert.Null(value); + } + + [Fact] + public void GetNullableStruct_WhenNull_ReturnsNull() + { + var dictionary = new Dictionary(); + ModelBase.Set(dictionary, "key", null); + + var value = ModelBase.GetNullableStruct(dictionary, "key"); + + Assert.Null(value); + } + + [Fact] + public void GetNullableStruct_WhenMismatchedType_Throws() + { + var dictionary = new Dictionary(); + ModelBase.Set(dictionary, "key", "value"); + + var exception = Assert.Throws(() => + ModelBase.GetNullableStruct(dictionary, "key") + ); + + Assert.Equal("'key' must be of type System.Int32", exception.Message); + } +} diff --git a/src/Anthropic.Tests/Models/APIErrorObjectTest.cs b/src/Anthropic.Tests/Models/APIErrorObjectTest.cs new file mode 100644 index 00000000..1cdf1244 --- /dev/null +++ b/src/Anthropic.Tests/Models/APIErrorObjectTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models; + +namespace Anthropic.Tests.Models; + +public class APIErrorObjectTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new APIErrorObject { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"api_error\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new APIErrorObject { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new APIErrorObject { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"api_error\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new APIErrorObject { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/AuthenticationErrorTest.cs b/src/Anthropic.Tests/Models/AuthenticationErrorTest.cs new file mode 100644 index 00000000..d2ca47b3 --- /dev/null +++ b/src/Anthropic.Tests/Models/AuthenticationErrorTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models; + +namespace Anthropic.Tests.Models; + +public class AuthenticationErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new AuthenticationError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"authentication_error\"" + ); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new AuthenticationError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new AuthenticationError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"authentication_error\"" + ); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new AuthenticationError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/AnthropicBetaTest.cs b/src/Anthropic.Tests/Models/Beta/AnthropicBetaTest.cs new file mode 100644 index 00000000..4fbab76d --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/AnthropicBetaTest.cs @@ -0,0 +1,96 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta; + +namespace Anthropic.Tests.Models.Beta; + +public class AnthropicBetaTest : TestBase +{ + [Theory] + [InlineData(AnthropicBeta.MessageBatches2024_09_24)] + [InlineData(AnthropicBeta.PromptCaching2024_07_31)] + [InlineData(AnthropicBeta.ComputerUse2024_10_22)] + [InlineData(AnthropicBeta.ComputerUse2025_01_24)] + [InlineData(AnthropicBeta.PDFs2024_09_25)] + [InlineData(AnthropicBeta.TokenCounting2024_11_01)] + [InlineData(AnthropicBeta.TokenEfficientTools2025_02_19)] + [InlineData(AnthropicBeta.Output128k2025_02_19)] + [InlineData(AnthropicBeta.FilesAPI2025_04_14)] + [InlineData(AnthropicBeta.MCPClient2025_04_04)] + [InlineData(AnthropicBeta.MCPClient2025_11_20)] + [InlineData(AnthropicBeta.DevFullThinking2025_05_14)] + [InlineData(AnthropicBeta.InterleavedThinking2025_05_14)] + [InlineData(AnthropicBeta.CodeExecution2025_05_22)] + [InlineData(AnthropicBeta.ExtendedCacheTTL2025_04_11)] + [InlineData(AnthropicBeta.Context1m2025_08_07)] + [InlineData(AnthropicBeta.ContextManagement2025_06_27)] + [InlineData(AnthropicBeta.ModelContextWindowExceeded2025_08_26)] + [InlineData(AnthropicBeta.Skills2025_10_02)] + public void Validation_Works(AnthropicBeta rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(AnthropicBeta.MessageBatches2024_09_24)] + [InlineData(AnthropicBeta.PromptCaching2024_07_31)] + [InlineData(AnthropicBeta.ComputerUse2024_10_22)] + [InlineData(AnthropicBeta.ComputerUse2025_01_24)] + [InlineData(AnthropicBeta.PDFs2024_09_25)] + [InlineData(AnthropicBeta.TokenCounting2024_11_01)] + [InlineData(AnthropicBeta.TokenEfficientTools2025_02_19)] + [InlineData(AnthropicBeta.Output128k2025_02_19)] + [InlineData(AnthropicBeta.FilesAPI2025_04_14)] + [InlineData(AnthropicBeta.MCPClient2025_04_04)] + [InlineData(AnthropicBeta.MCPClient2025_11_20)] + [InlineData(AnthropicBeta.DevFullThinking2025_05_14)] + [InlineData(AnthropicBeta.InterleavedThinking2025_05_14)] + [InlineData(AnthropicBeta.CodeExecution2025_05_22)] + [InlineData(AnthropicBeta.ExtendedCacheTTL2025_04_11)] + [InlineData(AnthropicBeta.Context1m2025_08_07)] + [InlineData(AnthropicBeta.ContextManagement2025_06_27)] + [InlineData(AnthropicBeta.ModelContextWindowExceeded2025_08_26)] + [InlineData(AnthropicBeta.Skills2025_10_02)] + public void SerializationRoundtrip_Works(AnthropicBeta rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/BetaAPIErrorTest.cs b/src/Anthropic.Tests/Models/Beta/BetaAPIErrorTest.cs new file mode 100644 index 00000000..03b43a07 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/BetaAPIErrorTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta; + +namespace Anthropic.Tests.Models.Beta; + +public class BetaAPIErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaAPIError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"api_error\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaAPIError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaAPIError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"api_error\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaAPIError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/BetaAuthenticationErrorTest.cs b/src/Anthropic.Tests/Models/Beta/BetaAuthenticationErrorTest.cs new file mode 100644 index 00000000..018a21a9 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/BetaAuthenticationErrorTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Beta; + +namespace Anthropic.Tests.Models.Beta; + +public class BetaAuthenticationErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaAuthenticationError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"authentication_error\"" + ); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaAuthenticationError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaAuthenticationError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"authentication_error\"" + ); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaAuthenticationError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/BetaBillingErrorTest.cs b/src/Anthropic.Tests/Models/Beta/BetaBillingErrorTest.cs new file mode 100644 index 00000000..16028664 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/BetaBillingErrorTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta; + +namespace Anthropic.Tests.Models.Beta; + +public class BetaBillingErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaBillingError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"billing_error\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaBillingError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaBillingError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"billing_error\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaBillingError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/BetaErrorResponseTest.cs b/src/Anthropic.Tests/Models/Beta/BetaErrorResponseTest.cs new file mode 100644 index 00000000..086604ee --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/BetaErrorResponseTest.cs @@ -0,0 +1,74 @@ +using System.Text.Json; +using Anthropic.Models.Beta; + +namespace Anthropic.Tests.Models.Beta; + +public class BetaErrorResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaErrorResponse + { + Error = new BetaInvalidRequestError("message"), + RequestID = "request_id", + }; + + BetaError expectedError = new BetaInvalidRequestError("message"); + string expectedRequestID = "request_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"error\""); + + Assert.Equal(expectedError, model.Error); + Assert.Equal(expectedRequestID, model.RequestID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaErrorResponse + { + Error = new BetaInvalidRequestError("message"), + RequestID = "request_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaErrorResponse + { + Error = new BetaInvalidRequestError("message"), + RequestID = "request_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaError expectedError = new BetaInvalidRequestError("message"); + string expectedRequestID = "request_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"error\""); + + Assert.Equal(expectedError, deserialized.Error); + Assert.Equal(expectedRequestID, deserialized.RequestID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaErrorResponse + { + Error = new BetaInvalidRequestError("message"), + RequestID = "request_id", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/BetaErrorTest.cs b/src/Anthropic.Tests/Models/Beta/BetaErrorTest.cs new file mode 100644 index 00000000..6c9258ec --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/BetaErrorTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta; diff --git a/src/Anthropic.Tests/Models/Beta/BetaGatewayTimeoutErrorTest.cs b/src/Anthropic.Tests/Models/Beta/BetaGatewayTimeoutErrorTest.cs new file mode 100644 index 00000000..e3f4be1c --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/BetaGatewayTimeoutErrorTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta; + +namespace Anthropic.Tests.Models.Beta; + +public class BetaGatewayTimeoutErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaGatewayTimeoutError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"timeout_error\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaGatewayTimeoutError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaGatewayTimeoutError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"timeout_error\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaGatewayTimeoutError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/BetaInvalidRequestErrorTest.cs b/src/Anthropic.Tests/Models/Beta/BetaInvalidRequestErrorTest.cs new file mode 100644 index 00000000..88c6706f --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/BetaInvalidRequestErrorTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Beta; + +namespace Anthropic.Tests.Models.Beta; + +public class BetaInvalidRequestErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaInvalidRequestError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"invalid_request_error\"" + ); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaInvalidRequestError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaInvalidRequestError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"invalid_request_error\"" + ); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaInvalidRequestError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/BetaNotFoundErrorTest.cs b/src/Anthropic.Tests/Models/Beta/BetaNotFoundErrorTest.cs new file mode 100644 index 00000000..ba870192 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/BetaNotFoundErrorTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta; + +namespace Anthropic.Tests.Models.Beta; + +public class BetaNotFoundErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaNotFoundError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"not_found_error\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaNotFoundError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaNotFoundError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"not_found_error\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaNotFoundError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/BetaOverloadedErrorTest.cs b/src/Anthropic.Tests/Models/Beta/BetaOverloadedErrorTest.cs new file mode 100644 index 00000000..6829f315 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/BetaOverloadedErrorTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta; + +namespace Anthropic.Tests.Models.Beta; + +public class BetaOverloadedErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaOverloadedError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"overloaded_error\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaOverloadedError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaOverloadedError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"overloaded_error\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaOverloadedError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/BetaPermissionErrorTest.cs b/src/Anthropic.Tests/Models/Beta/BetaPermissionErrorTest.cs new file mode 100644 index 00000000..38c9240c --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/BetaPermissionErrorTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta; + +namespace Anthropic.Tests.Models.Beta; + +public class BetaPermissionErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaPermissionError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"permission_error\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaPermissionError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaPermissionError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"permission_error\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaPermissionError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/BetaRateLimitErrorTest.cs b/src/Anthropic.Tests/Models/Beta/BetaRateLimitErrorTest.cs new file mode 100644 index 00000000..dd799408 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/BetaRateLimitErrorTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta; + +namespace Anthropic.Tests.Models.Beta; + +public class BetaRateLimitErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaRateLimitError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"rate_limit_error\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaRateLimitError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaRateLimitError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"rate_limit_error\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaRateLimitError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Files/DeletedFileTest.cs b/src/Anthropic.Tests/Models/Beta/Files/DeletedFileTest.cs new file mode 100644 index 00000000..141d782f --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Files/DeletedFileTest.cs @@ -0,0 +1,156 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Files; + +namespace Anthropic.Tests.Models.Beta.Files; + +public class DeletedFileTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new DeletedFile { ID = "id", Type = Type.FileDeleted }; + + string expectedID = "id"; + ApiEnum expectedType = Type.FileDeleted; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedType, model.Type); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new DeletedFile { ID = "id", Type = Type.FileDeleted }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new DeletedFile { ID = "id", Type = Type.FileDeleted }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "id"; + ApiEnum expectedType = Type.FileDeleted; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedType, deserialized.Type); + } + + [Fact] + public void Validation_Works() + { + var model = new DeletedFile { ID = "id", Type = Type.FileDeleted }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new DeletedFile { ID = "id" }; + + Assert.Null(model.Type); + Assert.False(model.RawData.ContainsKey("type")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new DeletedFile { ID = "id" }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new DeletedFile + { + ID = "id", + + // Null should be interpreted as omitted for these properties + Type = null, + }; + + Assert.Null(model.Type); + Assert.False(model.RawData.ContainsKey("type")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new DeletedFile + { + ID = "id", + + // Null should be interpreted as omitted for these properties + Type = null, + }; + + model.Validate(); + } +} + +public class TypeTest : TestBase +{ + [Theory] + [InlineData(Type.FileDeleted)] + public void Validation_Works(Type rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(Type.FileDeleted)] + public void SerializationRoundtrip_Works(Type rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Files/FileListPageResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Files/FileListPageResponseTest.cs new file mode 100644 index 00000000..75395cc3 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Files/FileListPageResponseTest.cs @@ -0,0 +1,370 @@ +using System; +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Files; + +namespace Anthropic.Tests.Models.Beta.Files; + +public class FileListPageResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new FileListPageResponse + { + Data = + [ + new() + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + List expectedData = + [ + new() + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }, + ]; + string expectedFirstID = "first_id"; + bool expectedHasMore = true; + string expectedLastID = "last_id"; + + Assert.Equal(expectedData.Count, model.Data.Count); + for (int i = 0; i < expectedData.Count; i++) + { + Assert.Equal(expectedData[i], model.Data[i]); + } + Assert.Equal(expectedFirstID, model.FirstID); + Assert.Equal(expectedHasMore, model.HasMore); + Assert.Equal(expectedLastID, model.LastID); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new FileListPageResponse + { + Data = + [ + new() + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new FileListPageResponse + { + Data = + [ + new() + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedData = + [ + new() + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }, + ]; + string expectedFirstID = "first_id"; + bool expectedHasMore = true; + string expectedLastID = "last_id"; + + Assert.Equal(expectedData.Count, deserialized.Data.Count); + for (int i = 0; i < expectedData.Count; i++) + { + Assert.Equal(expectedData[i], deserialized.Data[i]); + } + Assert.Equal(expectedFirstID, deserialized.FirstID); + Assert.Equal(expectedHasMore, deserialized.HasMore); + Assert.Equal(expectedLastID, deserialized.LastID); + } + + [Fact] + public void Validation_Works() + { + var model = new FileListPageResponse + { + Data = + [ + new() + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new FileListPageResponse + { + Data = + [ + new() + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }, + ], + FirstID = "first_id", + LastID = "last_id", + }; + + Assert.Null(model.HasMore); + Assert.False(model.RawData.ContainsKey("has_more")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new FileListPageResponse + { + Data = + [ + new() + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }, + ], + FirstID = "first_id", + LastID = "last_id", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new FileListPageResponse + { + Data = + [ + new() + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }, + ], + FirstID = "first_id", + LastID = "last_id", + + // Null should be interpreted as omitted for these properties + HasMore = null, + }; + + Assert.Null(model.HasMore); + Assert.False(model.RawData.ContainsKey("has_more")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new FileListPageResponse + { + Data = + [ + new() + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }, + ], + FirstID = "first_id", + LastID = "last_id", + + // Null should be interpreted as omitted for these properties + HasMore = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new FileListPageResponse + { + Data = + [ + new() + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }, + ], + HasMore = true, + }; + + Assert.Null(model.FirstID); + Assert.False(model.RawData.ContainsKey("first_id")); + Assert.Null(model.LastID); + Assert.False(model.RawData.ContainsKey("last_id")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new FileListPageResponse + { + Data = + [ + new() + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }, + ], + HasMore = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new FileListPageResponse + { + Data = + [ + new() + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }, + ], + HasMore = true, + + FirstID = null, + LastID = null, + }; + + Assert.Null(model.FirstID); + Assert.True(model.RawData.ContainsKey("first_id")); + Assert.Null(model.LastID); + Assert.True(model.RawData.ContainsKey("last_id")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new FileListPageResponse + { + Data = + [ + new() + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }, + ], + HasMore = true, + + FirstID = null, + LastID = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Files/FileMetadataTest.cs b/src/Anthropic.Tests/Models/Beta/Files/FileMetadataTest.cs new file mode 100644 index 00000000..a0a59f27 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Files/FileMetadataTest.cs @@ -0,0 +1,175 @@ +using System; +using System.Text.Json; +using Anthropic.Models.Beta.Files; + +namespace Anthropic.Tests.Models.Beta.Files; + +public class FileMetadataTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new FileMetadata + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }; + + string expectedID = "id"; + DateTimeOffset expectedCreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"); + string expectedFilename = "x"; + string expectedMimeType = "x"; + long expectedSizeBytes = 0; + JsonElement expectedType = JsonSerializer.Deserialize("\"file\""); + bool expectedDownloadable = true; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedCreatedAt, model.CreatedAt); + Assert.Equal(expectedFilename, model.Filename); + Assert.Equal(expectedMimeType, model.MimeType); + Assert.Equal(expectedSizeBytes, model.SizeBytes); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedDownloadable, model.Downloadable); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new FileMetadata + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new FileMetadata + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "id"; + DateTimeOffset expectedCreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"); + string expectedFilename = "x"; + string expectedMimeType = "x"; + long expectedSizeBytes = 0; + JsonElement expectedType = JsonSerializer.Deserialize("\"file\""); + bool expectedDownloadable = true; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedCreatedAt, deserialized.CreatedAt); + Assert.Equal(expectedFilename, deserialized.Filename); + Assert.Equal(expectedMimeType, deserialized.MimeType); + Assert.Equal(expectedSizeBytes, deserialized.SizeBytes); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedDownloadable, deserialized.Downloadable); + } + + [Fact] + public void Validation_Works() + { + var model = new FileMetadata + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + Downloadable = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new FileMetadata + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + }; + + Assert.Null(model.Downloadable); + Assert.False(model.RawData.ContainsKey("downloadable")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new FileMetadata + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new FileMetadata + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + + // Null should be interpreted as omitted for these properties + Downloadable = null, + }; + + Assert.Null(model.Downloadable); + Assert.False(model.RawData.ContainsKey("downloadable")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new FileMetadata + { + ID = "id", + CreatedAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Filename = "x", + MimeType = "x", + SizeBytes = 0, + + // Null should be interpreted as omitted for these properties + Downloadable = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/Batches/BatchCreateParamsTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BatchCreateParamsTest.cs new file mode 100644 index 00000000..89cd6bd5 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BatchCreateParamsTest.cs @@ -0,0 +1,2176 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages.Batches; +using Messages = Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages.Batches; + +public class RequestTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Request + { + CustomID = "my-custom-id-1", + Params = new() + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + Container = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }, + ContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }, + MCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ], + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + OutputConfig = new() { Effort = Messages::Effort.Low }, + OutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::BetaThinkingConfigEnabled(1024), + ToolChoice = new Messages::BetaToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }, + }; + + string expectedCustomID = "my-custom-id-1"; + Params expectedParams = new() + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + Container = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }, + ContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }, + MCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ], + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + OutputConfig = new() { Effort = Messages::Effort.Low }, + OutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::BetaThinkingConfigEnabled(1024), + ToolChoice = new Messages::BetaToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }; + + Assert.Equal(expectedCustomID, model.CustomID); + Assert.Equal(expectedParams, model.Params); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Request + { + CustomID = "my-custom-id-1", + Params = new() + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + Container = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }, + ContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }, + MCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ], + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + OutputConfig = new() { Effort = Messages::Effort.Low }, + OutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::BetaThinkingConfigEnabled(1024), + ToolChoice = new Messages::BetaToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Request + { + CustomID = "my-custom-id-1", + Params = new() + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + Container = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }, + ContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }, + MCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ], + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + OutputConfig = new() { Effort = Messages::Effort.Low }, + OutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::BetaThinkingConfigEnabled(1024), + ToolChoice = new Messages::BetaToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCustomID = "my-custom-id-1"; + Params expectedParams = new() + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + Container = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }, + ContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }, + MCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ], + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + OutputConfig = new() { Effort = Messages::Effort.Low }, + OutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::BetaThinkingConfigEnabled(1024), + ToolChoice = new Messages::BetaToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }; + + Assert.Equal(expectedCustomID, deserialized.CustomID); + Assert.Equal(expectedParams, deserialized.Params); + } + + [Fact] + public void Validation_Works() + { + var model = new Request + { + CustomID = "my-custom-id-1", + Params = new() + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + Container = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }, + ContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }, + MCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ], + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + OutputConfig = new() { Effort = Messages::Effort.Low }, + OutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::BetaThinkingConfigEnabled(1024), + ToolChoice = new Messages::BetaToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }, + }; + + model.Validate(); + } +} + +public class ParamsTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + Container = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }, + ContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }, + MCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ], + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + OutputConfig = new() { Effort = Messages::Effort.Low }, + OutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::BetaThinkingConfigEnabled(1024), + ToolChoice = new Messages::BetaToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }; + + long expectedMaxTokens = 1024; + List expectedMessages = + [ + new() { Content = "Hello, world", Role = Messages::Role.User }, + ]; + ApiEnum expectedModel = global::Anthropic + .Models + .Messages + .Model + .ClaudeOpus4_5_20251101; + Container expectedContainer = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }; + Messages::BetaContextManagementConfig expectedContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }; + List expectedMCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ]; + Messages::BetaMetadata expectedMetadata = new() + { + UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b", + }; + Messages::BetaOutputConfig expectedOutputConfig = new() { Effort = Messages::Effort.Low }; + Messages::BetaJSONOutputFormat expectedOutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }; + ApiEnum expectedServiceTier = ServiceTier.Auto; + List expectedStopSequences = ["string"]; + bool expectedStream = true; + ParamsSystem expectedSystem = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ); + double expectedTemperature = 1; + Messages::BetaThinkingConfigParam expectedThinking = + new Messages::BetaThinkingConfigEnabled(1024); + Messages::BetaToolChoice expectedToolChoice = new Messages::BetaToolChoiceAuto() + { + DisableParallelToolUse = true, + }; + List expectedTools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ]; + long expectedTopK = 5; + double expectedTopP = 0.7; + + Assert.Equal(expectedMaxTokens, model.MaxTokens); + Assert.Equal(expectedMessages.Count, model.Messages.Count); + for (int i = 0; i < expectedMessages.Count; i++) + { + Assert.Equal(expectedMessages[i], model.Messages[i]); + } + Assert.Equal(expectedModel, model.Model); + Assert.Equal(expectedContainer, model.Container); + Assert.Equal(expectedContextManagement, model.ContextManagement); + Assert.Equal(expectedMCPServers.Count, model.MCPServers.Count); + for (int i = 0; i < expectedMCPServers.Count; i++) + { + Assert.Equal(expectedMCPServers[i], model.MCPServers[i]); + } + Assert.Equal(expectedMetadata, model.Metadata); + Assert.Equal(expectedOutputConfig, model.OutputConfig); + Assert.Equal(expectedOutputFormat, model.OutputFormat); + Assert.Equal(expectedServiceTier, model.ServiceTier); + Assert.Equal(expectedStopSequences.Count, model.StopSequences.Count); + for (int i = 0; i < expectedStopSequences.Count; i++) + { + Assert.Equal(expectedStopSequences[i], model.StopSequences[i]); + } + Assert.Equal(expectedStream, model.Stream); + Assert.Equal(expectedSystem, model.System); + Assert.Equal(expectedTemperature, model.Temperature); + Assert.Equal(expectedThinking, model.Thinking); + Assert.Equal(expectedToolChoice, model.ToolChoice); + Assert.Equal(expectedTools.Count, model.Tools.Count); + for (int i = 0; i < expectedTools.Count; i++) + { + Assert.Equal(expectedTools[i], model.Tools[i]); + } + Assert.Equal(expectedTopK, model.TopK); + Assert.Equal(expectedTopP, model.TopP); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + Container = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }, + ContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }, + MCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ], + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + OutputConfig = new() { Effort = Messages::Effort.Low }, + OutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::BetaThinkingConfigEnabled(1024), + ToolChoice = new Messages::BetaToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + Container = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }, + ContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }, + MCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ], + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + OutputConfig = new() { Effort = Messages::Effort.Low }, + OutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::BetaThinkingConfigEnabled(1024), + ToolChoice = new Messages::BetaToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedMaxTokens = 1024; + List expectedMessages = + [ + new() { Content = "Hello, world", Role = Messages::Role.User }, + ]; + ApiEnum expectedModel = global::Anthropic + .Models + .Messages + .Model + .ClaudeOpus4_5_20251101; + Container expectedContainer = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }; + Messages::BetaContextManagementConfig expectedContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }; + List expectedMCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ]; + Messages::BetaMetadata expectedMetadata = new() + { + UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b", + }; + Messages::BetaOutputConfig expectedOutputConfig = new() { Effort = Messages::Effort.Low }; + Messages::BetaJSONOutputFormat expectedOutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }; + ApiEnum expectedServiceTier = ServiceTier.Auto; + List expectedStopSequences = ["string"]; + bool expectedStream = true; + ParamsSystem expectedSystem = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ); + double expectedTemperature = 1; + Messages::BetaThinkingConfigParam expectedThinking = + new Messages::BetaThinkingConfigEnabled(1024); + Messages::BetaToolChoice expectedToolChoice = new Messages::BetaToolChoiceAuto() + { + DisableParallelToolUse = true, + }; + List expectedTools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ]; + long expectedTopK = 5; + double expectedTopP = 0.7; + + Assert.Equal(expectedMaxTokens, deserialized.MaxTokens); + Assert.Equal(expectedMessages.Count, deserialized.Messages.Count); + for (int i = 0; i < expectedMessages.Count; i++) + { + Assert.Equal(expectedMessages[i], deserialized.Messages[i]); + } + Assert.Equal(expectedModel, deserialized.Model); + Assert.Equal(expectedContainer, deserialized.Container); + Assert.Equal(expectedContextManagement, deserialized.ContextManagement); + Assert.Equal(expectedMCPServers.Count, deserialized.MCPServers.Count); + for (int i = 0; i < expectedMCPServers.Count; i++) + { + Assert.Equal(expectedMCPServers[i], deserialized.MCPServers[i]); + } + Assert.Equal(expectedMetadata, deserialized.Metadata); + Assert.Equal(expectedOutputConfig, deserialized.OutputConfig); + Assert.Equal(expectedOutputFormat, deserialized.OutputFormat); + Assert.Equal(expectedServiceTier, deserialized.ServiceTier); + Assert.Equal(expectedStopSequences.Count, deserialized.StopSequences.Count); + for (int i = 0; i < expectedStopSequences.Count; i++) + { + Assert.Equal(expectedStopSequences[i], deserialized.StopSequences[i]); + } + Assert.Equal(expectedStream, deserialized.Stream); + Assert.Equal(expectedSystem, deserialized.System); + Assert.Equal(expectedTemperature, deserialized.Temperature); + Assert.Equal(expectedThinking, deserialized.Thinking); + Assert.Equal(expectedToolChoice, deserialized.ToolChoice); + Assert.Equal(expectedTools.Count, deserialized.Tools.Count); + for (int i = 0; i < expectedTools.Count; i++) + { + Assert.Equal(expectedTools[i], deserialized.Tools[i]); + } + Assert.Equal(expectedTopK, deserialized.TopK); + Assert.Equal(expectedTopP, deserialized.TopP); + } + + [Fact] + public void Validation_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + Container = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }, + ContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }, + MCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ], + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + OutputConfig = new() { Effort = Messages::Effort.Low }, + OutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::BetaThinkingConfigEnabled(1024), + ToolChoice = new Messages::BetaToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + Container = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }, + ContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }, + OutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }, + }; + + Assert.Null(model.MCPServers); + Assert.False(model.RawData.ContainsKey("mcp_servers")); + Assert.Null(model.Metadata); + Assert.False(model.RawData.ContainsKey("metadata")); + Assert.Null(model.OutputConfig); + Assert.False(model.RawData.ContainsKey("output_config")); + Assert.Null(model.ServiceTier); + Assert.False(model.RawData.ContainsKey("service_tier")); + Assert.Null(model.StopSequences); + Assert.False(model.RawData.ContainsKey("stop_sequences")); + Assert.Null(model.Stream); + Assert.False(model.RawData.ContainsKey("stream")); + Assert.Null(model.System); + Assert.False(model.RawData.ContainsKey("system")); + Assert.Null(model.Temperature); + Assert.False(model.RawData.ContainsKey("temperature")); + Assert.Null(model.Thinking); + Assert.False(model.RawData.ContainsKey("thinking")); + Assert.Null(model.ToolChoice); + Assert.False(model.RawData.ContainsKey("tool_choice")); + Assert.Null(model.Tools); + Assert.False(model.RawData.ContainsKey("tools")); + Assert.Null(model.TopK); + Assert.False(model.RawData.ContainsKey("top_k")); + Assert.Null(model.TopP); + Assert.False(model.RawData.ContainsKey("top_p")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + Container = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }, + ContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }, + OutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + Container = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }, + ContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }, + OutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }, + + // Null should be interpreted as omitted for these properties + MCPServers = null, + Metadata = null, + OutputConfig = null, + ServiceTier = null, + StopSequences = null, + Stream = null, + System = null, + Temperature = null, + Thinking = null, + ToolChoice = null, + Tools = null, + TopK = null, + TopP = null, + }; + + Assert.Null(model.MCPServers); + Assert.False(model.RawData.ContainsKey("mcp_servers")); + Assert.Null(model.Metadata); + Assert.False(model.RawData.ContainsKey("metadata")); + Assert.Null(model.OutputConfig); + Assert.False(model.RawData.ContainsKey("output_config")); + Assert.Null(model.ServiceTier); + Assert.False(model.RawData.ContainsKey("service_tier")); + Assert.Null(model.StopSequences); + Assert.False(model.RawData.ContainsKey("stop_sequences")); + Assert.Null(model.Stream); + Assert.False(model.RawData.ContainsKey("stream")); + Assert.Null(model.System); + Assert.False(model.RawData.ContainsKey("system")); + Assert.Null(model.Temperature); + Assert.False(model.RawData.ContainsKey("temperature")); + Assert.Null(model.Thinking); + Assert.False(model.RawData.ContainsKey("thinking")); + Assert.Null(model.ToolChoice); + Assert.False(model.RawData.ContainsKey("tool_choice")); + Assert.Null(model.Tools); + Assert.False(model.RawData.ContainsKey("tools")); + Assert.Null(model.TopK); + Assert.False(model.RawData.ContainsKey("top_k")); + Assert.Null(model.TopP); + Assert.False(model.RawData.ContainsKey("top_p")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + Container = new Messages::BetaContainerParams() + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }, + ContextManagement = new() + { + Edits = + [ + new Messages::BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new Messages::BetaInputTokensTrigger(1), + }, + ], + }, + OutputFormat = new() + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }, + + // Null should be interpreted as omitted for these properties + MCPServers = null, + Metadata = null, + OutputConfig = null, + ServiceTier = null, + StopSequences = null, + Stream = null, + System = null, + Temperature = null, + Thinking = null, + ToolChoice = null, + Tools = null, + TopK = null, + TopP = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + MCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ], + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + OutputConfig = new() { Effort = Messages::Effort.Low }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::BetaThinkingConfigEnabled(1024), + ToolChoice = new Messages::BetaToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }; + + Assert.Null(model.Container); + Assert.False(model.RawData.ContainsKey("container")); + Assert.Null(model.ContextManagement); + Assert.False(model.RawData.ContainsKey("context_management")); + Assert.Null(model.OutputFormat); + Assert.False(model.RawData.ContainsKey("output_format")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + MCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ], + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + OutputConfig = new() { Effort = Messages::Effort.Low }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::BetaThinkingConfigEnabled(1024), + ToolChoice = new Messages::BetaToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + MCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ], + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + OutputConfig = new() { Effort = Messages::Effort.Low }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::BetaThinkingConfigEnabled(1024), + ToolChoice = new Messages::BetaToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + + Container = null, + ContextManagement = null, + OutputFormat = null, + }; + + Assert.Null(model.Container); + Assert.True(model.RawData.ContainsKey("container")); + Assert.Null(model.ContextManagement); + Assert.True(model.RawData.ContainsKey("context_management")); + Assert.Null(model.OutputFormat); + Assert.True(model.RawData.ContainsKey("output_format")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, + MCPServers = + [ + new() + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }, + ], + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + OutputConfig = new() { Effort = Messages::Effort.Low }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::BetaThinkingConfigEnabled(1024), + ToolChoice = new Messages::BetaToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::BetaTool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [Messages::BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = Messages::BetaToolType.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + + Container = null, + ContextManagement = null, + OutputFormat = null, + }; + + model.Validate(); + } +} + +public class ServiceTierTest : TestBase +{ + [Theory] + [InlineData(ServiceTier.Auto)] + [InlineData(ServiceTier.StandardOnly)] + public void Validation_Works(ServiceTier rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(ServiceTier.Auto)] + [InlineData(ServiceTier.StandardOnly)] + public void SerializationRoundtrip_Works(ServiceTier rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/Batches/BatchListPageResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BatchListPageResponseTest.cs new file mode 100644 index 00000000..a0745389 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BatchListPageResponseTest.cs @@ -0,0 +1,228 @@ +using System; +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages.Batches; + +namespace Anthropic.Tests.Models.Beta.Messages.Batches; + +public class BatchListPageResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BatchListPageResponse + { + Data = + [ + new() + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + List expectedData = + [ + new() + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }, + ]; + string expectedFirstID = "first_id"; + bool expectedHasMore = true; + string expectedLastID = "last_id"; + + Assert.Equal(expectedData.Count, model.Data.Count); + for (int i = 0; i < expectedData.Count; i++) + { + Assert.Equal(expectedData[i], model.Data[i]); + } + Assert.Equal(expectedFirstID, model.FirstID); + Assert.Equal(expectedHasMore, model.HasMore); + Assert.Equal(expectedLastID, model.LastID); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BatchListPageResponse + { + Data = + [ + new() + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BatchListPageResponse + { + Data = + [ + new() + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedData = + [ + new() + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }, + ]; + string expectedFirstID = "first_id"; + bool expectedHasMore = true; + string expectedLastID = "last_id"; + + Assert.Equal(expectedData.Count, deserialized.Data.Count); + for (int i = 0; i < expectedData.Count; i++) + { + Assert.Equal(expectedData[i], deserialized.Data[i]); + } + Assert.Equal(expectedFirstID, deserialized.FirstID); + Assert.Equal(expectedHasMore, deserialized.HasMore); + Assert.Equal(expectedLastID, deserialized.LastID); + } + + [Fact] + public void Validation_Works() + { + var model = new BatchListPageResponse + { + Data = + [ + new() + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaDeletedMessageBatchTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaDeletedMessageBatchTest.cs new file mode 100644 index 00000000..30c0e4c3 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaDeletedMessageBatchTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages.Batches; + +namespace Anthropic.Tests.Models.Beta.Messages.Batches; + +public class BetaDeletedMessageBatchTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaDeletedMessageBatch { ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF" }; + + string expectedID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"message_batch_deleted\"" + ); + + Assert.Equal(expectedID, model.ID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaDeletedMessageBatch { ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaDeletedMessageBatch { ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"message_batch_deleted\"" + ); + + Assert.Equal(expectedID, deserialized.ID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaDeletedMessageBatch { ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchCanceledResultTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchCanceledResultTest.cs new file mode 100644 index 00000000..5abf6f08 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchCanceledResultTest.cs @@ -0,0 +1,50 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages.Batches; + +namespace Anthropic.Tests.Models.Beta.Messages.Batches; + +public class BetaMessageBatchCanceledResultTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMessageBatchCanceledResult { }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"canceled\""); + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMessageBatchCanceledResult { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMessageBatchCanceledResult { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"canceled\""); + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMessageBatchCanceledResult { }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchErroredResultTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchErroredResultTest.cs new file mode 100644 index 00000000..2cf7c8c1 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchErroredResultTest.cs @@ -0,0 +1,91 @@ +using System.Text.Json; +using Anthropic.Models.Beta; +using Anthropic.Models.Beta.Messages.Batches; + +namespace Anthropic.Tests.Models.Beta.Messages.Batches; + +public class BetaMessageBatchErroredResultTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMessageBatchErroredResult + { + Error = new() + { + Error = new BetaInvalidRequestError("message"), + RequestID = "request_id", + }, + }; + + BetaErrorResponse expectedError = new() + { + Error = new BetaInvalidRequestError("message"), + RequestID = "request_id", + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"errored\""); + + Assert.Equal(expectedError, model.Error); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMessageBatchErroredResult + { + Error = new() + { + Error = new BetaInvalidRequestError("message"), + RequestID = "request_id", + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMessageBatchErroredResult + { + Error = new() + { + Error = new BetaInvalidRequestError("message"), + RequestID = "request_id", + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaErrorResponse expectedError = new() + { + Error = new BetaInvalidRequestError("message"), + RequestID = "request_id", + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"errored\""); + + Assert.Equal(expectedError, deserialized.Error); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMessageBatchErroredResult + { + Error = new() + { + Error = new BetaInvalidRequestError("message"), + RequestID = "request_id", + }, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchExpiredResultTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchExpiredResultTest.cs new file mode 100644 index 00000000..61c74f7d --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchExpiredResultTest.cs @@ -0,0 +1,50 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages.Batches; + +namespace Anthropic.Tests.Models.Beta.Messages.Batches; + +public class BetaMessageBatchExpiredResultTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMessageBatchExpiredResult { }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"expired\""); + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMessageBatchExpiredResult { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMessageBatchExpiredResult { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"expired\""); + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMessageBatchExpiredResult { }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchIndividualResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchIndividualResponseTest.cs new file mode 100644 index 00000000..74aec9fa --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchIndividualResponseTest.cs @@ -0,0 +1,457 @@ +using System; +using System.Text.Json; +using Anthropic.Models.Beta.Messages.Batches; +using Anthropic.Models.Messages; +using Messages = Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages.Batches; + +public class BetaMessageBatchIndividualResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMessageBatchIndividualResponse + { + CustomID = "my-custom-id-1", + Result = new BetaMessageBatchSucceededResult( + new Messages::BetaMessage() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + } + ), + }; + + string expectedCustomID = "my-custom-id-1"; + BetaMessageBatchResult expectedResult = new BetaMessageBatchSucceededResult( + new Messages::BetaMessage() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + } + ); + + Assert.Equal(expectedCustomID, model.CustomID); + Assert.Equal(expectedResult, model.Result); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMessageBatchIndividualResponse + { + CustomID = "my-custom-id-1", + Result = new BetaMessageBatchSucceededResult( + new Messages::BetaMessage() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + } + ), + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMessageBatchIndividualResponse + { + CustomID = "my-custom-id-1", + Result = new BetaMessageBatchSucceededResult( + new Messages::BetaMessage() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + } + ), + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCustomID = "my-custom-id-1"; + BetaMessageBatchResult expectedResult = new BetaMessageBatchSucceededResult( + new Messages::BetaMessage() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + } + ); + + Assert.Equal(expectedCustomID, deserialized.CustomID); + Assert.Equal(expectedResult, deserialized.Result); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMessageBatchIndividualResponse + { + CustomID = "my-custom-id-1", + Result = new BetaMessageBatchSucceededResult( + new Messages::BetaMessage() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + } + ), + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchRequestCountsTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchRequestCountsTest.cs new file mode 100644 index 00000000..df481baf --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchRequestCountsTest.cs @@ -0,0 +1,94 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages.Batches; + +namespace Anthropic.Tests.Models.Beta.Messages.Batches; + +public class BetaMessageBatchRequestCountsTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMessageBatchRequestCounts + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }; + + long expectedCanceled = 10; + long expectedErrored = 30; + long expectedExpired = 10; + long expectedProcessing = 100; + long expectedSucceeded = 50; + + Assert.Equal(expectedCanceled, model.Canceled); + Assert.Equal(expectedErrored, model.Errored); + Assert.Equal(expectedExpired, model.Expired); + Assert.Equal(expectedProcessing, model.Processing); + Assert.Equal(expectedSucceeded, model.Succeeded); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMessageBatchRequestCounts + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMessageBatchRequestCounts + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedCanceled = 10; + long expectedErrored = 30; + long expectedExpired = 10; + long expectedProcessing = 100; + long expectedSucceeded = 50; + + Assert.Equal(expectedCanceled, deserialized.Canceled); + Assert.Equal(expectedErrored, deserialized.Errored); + Assert.Equal(expectedExpired, deserialized.Expired); + Assert.Equal(expectedProcessing, deserialized.Processing); + Assert.Equal(expectedSucceeded, deserialized.Succeeded); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMessageBatchRequestCounts + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchResultTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchResultTest.cs new file mode 100644 index 00000000..2c02ae6e --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchResultTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages.Batches; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchSucceededResultTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchSucceededResultTest.cs new file mode 100644 index 00000000..18e5749c --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchSucceededResultTest.cs @@ -0,0 +1,433 @@ +using System; +using System.Text.Json; +using Anthropic.Models.Beta.Messages.Batches; +using Anthropic.Models.Messages; +using Messages = Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages.Batches; + +public class BetaMessageBatchSucceededResultTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMessageBatchSucceededResult + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }, + }; + + Messages::BetaMessage expectedMessage = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"succeeded\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMessageBatchSucceededResult + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMessageBatchSucceededResult + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + Messages::BetaMessage expectedMessage = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"succeeded\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMessageBatchSucceededResult + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchTest.cs new file mode 100644 index 00000000..638ab9d4 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/Batches/BetaMessageBatchTest.cs @@ -0,0 +1,243 @@ +using System; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages.Batches; + +namespace Anthropic.Tests.Models.Beta.Messages.Batches; + +public class BetaMessageBatchTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMessageBatch + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }; + + string expectedID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF"; + DateTimeOffset expectedArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + DateTimeOffset expectedCancelInitiatedAt = DateTimeOffset.Parse( + "2024-08-20T18:37:24.100435Z" + ); + DateTimeOffset expectedCreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + DateTimeOffset expectedEndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + DateTimeOffset expectedExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + ApiEnum expectedProcessingStatus = ProcessingStatus.InProgress; + BetaMessageBatchRequestCounts expectedRequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }; + string expectedResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results"; + JsonElement expectedType = JsonSerializer.Deserialize("\"message_batch\""); + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedArchivedAt, model.ArchivedAt); + Assert.Equal(expectedCancelInitiatedAt, model.CancelInitiatedAt); + Assert.Equal(expectedCreatedAt, model.CreatedAt); + Assert.Equal(expectedEndedAt, model.EndedAt); + Assert.Equal(expectedExpiresAt, model.ExpiresAt); + Assert.Equal(expectedProcessingStatus, model.ProcessingStatus); + Assert.Equal(expectedRequestCounts, model.RequestCounts); + Assert.Equal(expectedResultsURL, model.ResultsURL); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMessageBatch + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMessageBatch + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF"; + DateTimeOffset expectedArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + DateTimeOffset expectedCancelInitiatedAt = DateTimeOffset.Parse( + "2024-08-20T18:37:24.100435Z" + ); + DateTimeOffset expectedCreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + DateTimeOffset expectedEndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + DateTimeOffset expectedExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + ApiEnum expectedProcessingStatus = ProcessingStatus.InProgress; + BetaMessageBatchRequestCounts expectedRequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }; + string expectedResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results"; + JsonElement expectedType = JsonSerializer.Deserialize("\"message_batch\""); + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedArchivedAt, deserialized.ArchivedAt); + Assert.Equal(expectedCancelInitiatedAt, deserialized.CancelInitiatedAt); + Assert.Equal(expectedCreatedAt, deserialized.CreatedAt); + Assert.Equal(expectedEndedAt, deserialized.EndedAt); + Assert.Equal(expectedExpiresAt, deserialized.ExpiresAt); + Assert.Equal(expectedProcessingStatus, deserialized.ProcessingStatus); + Assert.Equal(expectedRequestCounts, deserialized.RequestCounts); + Assert.Equal(expectedResultsURL, deserialized.ResultsURL); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMessageBatch + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }; + + model.Validate(); + } +} + +public class ProcessingStatusTest : TestBase +{ + [Theory] + [InlineData(ProcessingStatus.InProgress)] + [InlineData(ProcessingStatus.Canceling)] + [InlineData(ProcessingStatus.Ended)] + public void Validation_Works(ProcessingStatus rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(ProcessingStatus.InProgress)] + [InlineData(ProcessingStatus.Canceling)] + [InlineData(ProcessingStatus.Ended)] + public void SerializationRoundtrip_Works(ProcessingStatus rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaAllThinkingTurnsTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaAllThinkingTurnsTest.cs new file mode 100644 index 00000000..2e84c40f --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaAllThinkingTurnsTest.cs @@ -0,0 +1,50 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaAllThinkingTurnsTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaAllThinkingTurns { }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"all\""); + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaAllThinkingTurns { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaAllThinkingTurns { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"all\""); + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaAllThinkingTurns { }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaBase64ImageSourceTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaBase64ImageSourceTest.cs new file mode 100644 index 00000000..3b5bcbf5 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaBase64ImageSourceTest.cs @@ -0,0 +1,136 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaBase64ImageSourceTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaBase64ImageSource + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }; + + string expectedData = "U3RhaW5sZXNzIHJvY2tz"; + ApiEnum expectedMediaType = MediaType.ImageJPEG; + JsonElement expectedType = JsonSerializer.Deserialize("\"base64\""); + + Assert.Equal(expectedData, model.Data); + Assert.Equal(expectedMediaType, model.MediaType); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaBase64ImageSource + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaBase64ImageSource + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedData = "U3RhaW5sZXNzIHJvY2tz"; + ApiEnum expectedMediaType = MediaType.ImageJPEG; + JsonElement expectedType = JsonSerializer.Deserialize("\"base64\""); + + Assert.Equal(expectedData, deserialized.Data); + Assert.Equal(expectedMediaType, deserialized.MediaType); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaBase64ImageSource + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }; + + model.Validate(); + } +} + +public class MediaTypeTest : TestBase +{ + [Theory] + [InlineData(MediaType.ImageJPEG)] + [InlineData(MediaType.ImagePNG)] + [InlineData(MediaType.ImageGIF)] + [InlineData(MediaType.ImageWebP)] + public void Validation_Works(MediaType rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(MediaType.ImageJPEG)] + [InlineData(MediaType.ImagePNG)] + [InlineData(MediaType.ImageGIF)] + [InlineData(MediaType.ImageWebP)] + public void SerializationRoundtrip_Works(MediaType rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaBase64PDFSourceTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaBase64PDFSourceTest.cs new file mode 100644 index 00000000..425f2d17 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaBase64PDFSourceTest.cs @@ -0,0 +1,62 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaBase64PDFSourceTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaBase64PDFSource { Data = "U3RhaW5sZXNzIHJvY2tz" }; + + string expectedData = "U3RhaW5sZXNzIHJvY2tz"; + JsonElement expectedMediaType = JsonSerializer.Deserialize( + "\"application/pdf\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize("\"base64\""); + + Assert.Equal(expectedData, model.Data); + Assert.True(JsonElement.DeepEquals(expectedMediaType, model.MediaType)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaBase64PDFSource { Data = "U3RhaW5sZXNzIHJvY2tz" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaBase64PDFSource { Data = "U3RhaW5sZXNzIHJvY2tz" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedData = "U3RhaW5sZXNzIHJvY2tz"; + JsonElement expectedMediaType = JsonSerializer.Deserialize( + "\"application/pdf\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize("\"base64\""); + + Assert.Equal(expectedData, deserialized.Data); + Assert.True(JsonElement.DeepEquals(expectedMediaType, deserialized.MediaType)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaBase64PDFSource { Data = "U3RhaW5sZXNzIHJvY2tz" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionOutputBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionOutputBlockParamTest.cs new file mode 100644 index 00000000..c3bc3574 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionOutputBlockParamTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaBashCodeExecutionOutputBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaBashCodeExecutionOutputBlockParam { FileID = "file_id" }; + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_output\"" + ); + + Assert.Equal(expectedFileID, model.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaBashCodeExecutionOutputBlockParam { FileID = "file_id" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaBashCodeExecutionOutputBlockParam { FileID = "file_id" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_output\"" + ); + + Assert.Equal(expectedFileID, deserialized.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaBashCodeExecutionOutputBlockParam { FileID = "file_id" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionOutputBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionOutputBlockTest.cs new file mode 100644 index 00000000..8412747d --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionOutputBlockTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaBashCodeExecutionOutputBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaBashCodeExecutionOutputBlock { FileID = "file_id" }; + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_output\"" + ); + + Assert.Equal(expectedFileID, model.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaBashCodeExecutionOutputBlock { FileID = "file_id" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaBashCodeExecutionOutputBlock { FileID = "file_id" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_output\"" + ); + + Assert.Equal(expectedFileID, deserialized.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaBashCodeExecutionOutputBlock { FileID = "file_id" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionResultBlockParamTest.cs new file mode 100644 index 00000000..7be8a385 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionResultBlockParamTest.cs @@ -0,0 +1,103 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaBashCodeExecutionResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaBashCodeExecutionResultBlockParam + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + List expectedContent = [new("file_id")]; + long expectedReturnCode = 0; + string expectedStderr = "stderr"; + string expectedStdout = "stdout"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_result\"" + ); + + Assert.Equal(expectedContent.Count, model.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], model.Content[i]); + } + Assert.Equal(expectedReturnCode, model.ReturnCode); + Assert.Equal(expectedStderr, model.Stderr); + Assert.Equal(expectedStdout, model.Stdout); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaBashCodeExecutionResultBlockParam + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaBashCodeExecutionResultBlockParam + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedContent = [new("file_id")]; + long expectedReturnCode = 0; + string expectedStderr = "stderr"; + string expectedStdout = "stdout"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_result\"" + ); + + Assert.Equal(expectedContent.Count, deserialized.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], deserialized.Content[i]); + } + Assert.Equal(expectedReturnCode, deserialized.ReturnCode); + Assert.Equal(expectedStderr, deserialized.Stderr); + Assert.Equal(expectedStdout, deserialized.Stdout); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaBashCodeExecutionResultBlockParam + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionResultBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionResultBlockTest.cs new file mode 100644 index 00000000..3e15233c --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionResultBlockTest.cs @@ -0,0 +1,103 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaBashCodeExecutionResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaBashCodeExecutionResultBlock + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + List expectedContent = [new("file_id")]; + long expectedReturnCode = 0; + string expectedStderr = "stderr"; + string expectedStdout = "stdout"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_result\"" + ); + + Assert.Equal(expectedContent.Count, model.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], model.Content[i]); + } + Assert.Equal(expectedReturnCode, model.ReturnCode); + Assert.Equal(expectedStderr, model.Stderr); + Assert.Equal(expectedStdout, model.Stdout); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaBashCodeExecutionResultBlock + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaBashCodeExecutionResultBlock + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedContent = [new("file_id")]; + long expectedReturnCode = 0; + string expectedStderr = "stderr"; + string expectedStdout = "stdout"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_result\"" + ); + + Assert.Equal(expectedContent.Count, deserialized.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], deserialized.Content[i]); + } + Assert.Equal(expectedReturnCode, deserialized.ReturnCode); + Assert.Equal(expectedStderr, deserialized.Stderr); + Assert.Equal(expectedStdout, deserialized.Stdout); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaBashCodeExecutionResultBlock + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionToolResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionToolResultBlockParamTest.cs new file mode 100644 index 00000000..d0ad7657 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionToolResultBlockParamTest.cs @@ -0,0 +1,166 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaBashCodeExecutionToolResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaBashCodeExecutionToolResultBlockParam + { + Content = new BetaBashCodeExecutionToolResultErrorParam( + BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + BetaBashCodeExecutionToolResultBlockParamContent expectedContent = + new BetaBashCodeExecutionToolResultErrorParam( + BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_tool_result\"" + ); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaBashCodeExecutionToolResultBlockParam + { + Content = new BetaBashCodeExecutionToolResultErrorParam( + BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaBashCodeExecutionToolResultBlockParam + { + Content = new BetaBashCodeExecutionToolResultErrorParam( + BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + Assert.NotNull(deserialized); + + BetaBashCodeExecutionToolResultBlockParamContent expectedContent = + new BetaBashCodeExecutionToolResultErrorParam( + BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_tool_result\"" + ); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaBashCodeExecutionToolResultBlockParam + { + Content = new BetaBashCodeExecutionToolResultErrorParam( + BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaBashCodeExecutionToolResultBlockParam + { + Content = new BetaBashCodeExecutionToolResultErrorParam( + BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaBashCodeExecutionToolResultBlockParam + { + Content = new BetaBashCodeExecutionToolResultErrorParam( + BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaBashCodeExecutionToolResultBlockParam + { + Content = new BetaBashCodeExecutionToolResultErrorParam( + BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaBashCodeExecutionToolResultBlockParam + { + Content = new BetaBashCodeExecutionToolResultErrorParam( + BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionToolResultBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionToolResultBlockTest.cs new file mode 100644 index 00000000..2bb19fd9 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionToolResultBlockTest.cs @@ -0,0 +1,82 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaBashCodeExecutionToolResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaBashCodeExecutionToolResultBlock + { + Content = new BetaBashCodeExecutionToolResultError(ErrorCode.InvalidToolInput), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + Content expectedContent = new BetaBashCodeExecutionToolResultError( + ErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_tool_result\"" + ); + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaBashCodeExecutionToolResultBlock + { + Content = new BetaBashCodeExecutionToolResultError(ErrorCode.InvalidToolInput), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaBashCodeExecutionToolResultBlock + { + Content = new BetaBashCodeExecutionToolResultError(ErrorCode.InvalidToolInput), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + Content expectedContent = new BetaBashCodeExecutionToolResultError( + ErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_tool_result\"" + ); + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaBashCodeExecutionToolResultBlock + { + Content = new BetaBashCodeExecutionToolResultError(ErrorCode.InvalidToolInput), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionToolResultErrorParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionToolResultErrorParamTest.cs new file mode 100644 index 00000000..331611ae --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionToolResultErrorParamTest.cs @@ -0,0 +1,144 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaBashCodeExecutionToolResultErrorParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaBashCodeExecutionToolResultErrorParam + { + ErrorCode = BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + }; + + ApiEnum expectedErrorCode = + BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, model.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaBashCodeExecutionToolResultErrorParam + { + ErrorCode = BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaBashCodeExecutionToolResultErrorParam + { + ErrorCode = BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + Assert.NotNull(deserialized); + + ApiEnum expectedErrorCode = + BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, deserialized.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaBashCodeExecutionToolResultErrorParam + { + ErrorCode = BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + }; + + model.Validate(); + } +} + +public class BetaBashCodeExecutionToolResultErrorParamErrorCodeTest : TestBase +{ + [Theory] + [InlineData(BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput)] + [InlineData(BetaBashCodeExecutionToolResultErrorParamErrorCode.Unavailable)] + [InlineData(BetaBashCodeExecutionToolResultErrorParamErrorCode.TooManyRequests)] + [InlineData(BetaBashCodeExecutionToolResultErrorParamErrorCode.ExecutionTimeExceeded)] + [InlineData(BetaBashCodeExecutionToolResultErrorParamErrorCode.OutputFileTooLarge)] + public void Validation_Works(BetaBashCodeExecutionToolResultErrorParamErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaBashCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput)] + [InlineData(BetaBashCodeExecutionToolResultErrorParamErrorCode.Unavailable)] + [InlineData(BetaBashCodeExecutionToolResultErrorParamErrorCode.TooManyRequests)] + [InlineData(BetaBashCodeExecutionToolResultErrorParamErrorCode.ExecutionTimeExceeded)] + [InlineData(BetaBashCodeExecutionToolResultErrorParamErrorCode.OutputFileTooLarge)] + public void SerializationRoundtrip_Works( + BetaBashCodeExecutionToolResultErrorParamErrorCode rawValue + ) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionToolResultErrorTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionToolResultErrorTest.cs new file mode 100644 index 00000000..8cb8dd15 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaBashCodeExecutionToolResultErrorTest.cs @@ -0,0 +1,134 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaBashCodeExecutionToolResultErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaBashCodeExecutionToolResultError + { + ErrorCode = ErrorCode.InvalidToolInput, + }; + + ApiEnum expectedErrorCode = ErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, model.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaBashCodeExecutionToolResultError + { + ErrorCode = ErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaBashCodeExecutionToolResultError + { + ErrorCode = ErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ApiEnum expectedErrorCode = ErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"bash_code_execution_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, deserialized.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaBashCodeExecutionToolResultError + { + ErrorCode = ErrorCode.InvalidToolInput, + }; + + model.Validate(); + } +} + +public class ErrorCodeTest : TestBase +{ + [Theory] + [InlineData(ErrorCode.InvalidToolInput)] + [InlineData(ErrorCode.Unavailable)] + [InlineData(ErrorCode.TooManyRequests)] + [InlineData(ErrorCode.ExecutionTimeExceeded)] + [InlineData(ErrorCode.OutputFileTooLarge)] + public void Validation_Works(ErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(ErrorCode.InvalidToolInput)] + [InlineData(ErrorCode.Unavailable)] + [InlineData(ErrorCode.TooManyRequests)] + [InlineData(ErrorCode.ExecutionTimeExceeded)] + [InlineData(ErrorCode.OutputFileTooLarge)] + public void SerializationRoundtrip_Works(ErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCacheControlEphemeralTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCacheControlEphemeralTest.cs new file mode 100644 index 00000000..aadf5c96 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCacheControlEphemeralTest.cs @@ -0,0 +1,154 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCacheControlEphemeralTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCacheControlEphemeral { TTL = TTL.TTL5m }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"ephemeral\""); + ApiEnum expectedTTL = TTL.TTL5m; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedTTL, model.TTL); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCacheControlEphemeral { TTL = TTL.TTL5m }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCacheControlEphemeral { TTL = TTL.TTL5m }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"ephemeral\""); + ApiEnum expectedTTL = TTL.TTL5m; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedTTL, deserialized.TTL); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCacheControlEphemeral { TTL = TTL.TTL5m }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaCacheControlEphemeral { }; + + Assert.Null(model.TTL); + Assert.False(model.RawData.ContainsKey("ttl")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaCacheControlEphemeral { }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaCacheControlEphemeral + { + // Null should be interpreted as omitted for these properties + TTL = null, + }; + + Assert.Null(model.TTL); + Assert.False(model.RawData.ContainsKey("ttl")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaCacheControlEphemeral + { + // Null should be interpreted as omitted for these properties + TTL = null, + }; + + model.Validate(); + } +} + +public class TTLTest : TestBase +{ + [Theory] + [InlineData(TTL.TTL5m)] + [InlineData(TTL.TTL1h)] + public void Validation_Works(TTL rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(TTL.TTL5m)] + [InlineData(TTL.TTL1h)] + public void SerializationRoundtrip_Works(TTL rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCacheCreationTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCacheCreationTest.cs new file mode 100644 index 00000000..470119e0 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCacheCreationTest.cs @@ -0,0 +1,70 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCacheCreationTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCacheCreation + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }; + + long expectedEphemeral1hInputTokens = 0; + long expectedEphemeral5mInputTokens = 0; + + Assert.Equal(expectedEphemeral1hInputTokens, model.Ephemeral1hInputTokens); + Assert.Equal(expectedEphemeral5mInputTokens, model.Ephemeral5mInputTokens); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCacheCreation + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCacheCreation + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedEphemeral1hInputTokens = 0; + long expectedEphemeral5mInputTokens = 0; + + Assert.Equal(expectedEphemeral1hInputTokens, deserialized.Ephemeral1hInputTokens); + Assert.Equal(expectedEphemeral5mInputTokens, deserialized.Ephemeral5mInputTokens); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCacheCreation + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationCharLocationParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationCharLocationParamTest.cs new file mode 100644 index 00000000..a3c5f6ed --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationCharLocationParamTest.cs @@ -0,0 +1,98 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCitationCharLocationParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCitationCharLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }; + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "x"; + long expectedEndCharIndex = 0; + long expectedStartCharIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize("\"char_location\""); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedDocumentIndex, model.DocumentIndex); + Assert.Equal(expectedDocumentTitle, model.DocumentTitle); + Assert.Equal(expectedEndCharIndex, model.EndCharIndex); + Assert.Equal(expectedStartCharIndex, model.StartCharIndex); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCitationCharLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCitationCharLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "x"; + long expectedEndCharIndex = 0; + long expectedStartCharIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize("\"char_location\""); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedDocumentIndex, deserialized.DocumentIndex); + Assert.Equal(expectedDocumentTitle, deserialized.DocumentTitle); + Assert.Equal(expectedEndCharIndex, deserialized.EndCharIndex); + Assert.Equal(expectedStartCharIndex, deserialized.StartCharIndex); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCitationCharLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationCharLocationTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationCharLocationTest.cs new file mode 100644 index 00000000..8940a388 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationCharLocationTest.cs @@ -0,0 +1,106 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCitationCharLocationTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCitationCharLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }; + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "document_title"; + long expectedEndCharIndex = 0; + string expectedFileID = "file_id"; + long expectedStartCharIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize("\"char_location\""); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedDocumentIndex, model.DocumentIndex); + Assert.Equal(expectedDocumentTitle, model.DocumentTitle); + Assert.Equal(expectedEndCharIndex, model.EndCharIndex); + Assert.Equal(expectedFileID, model.FileID); + Assert.Equal(expectedStartCharIndex, model.StartCharIndex); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCitationCharLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCitationCharLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "document_title"; + long expectedEndCharIndex = 0; + string expectedFileID = "file_id"; + long expectedStartCharIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize("\"char_location\""); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedDocumentIndex, deserialized.DocumentIndex); + Assert.Equal(expectedDocumentTitle, deserialized.DocumentTitle); + Assert.Equal(expectedEndCharIndex, deserialized.EndCharIndex); + Assert.Equal(expectedFileID, deserialized.FileID); + Assert.Equal(expectedStartCharIndex, deserialized.StartCharIndex); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCitationCharLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationConfigTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationConfigTest.cs new file mode 100644 index 00000000..fc488e4a --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationConfigTest.cs @@ -0,0 +1,50 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCitationConfigTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCitationConfig { Enabled = true }; + + bool expectedEnabled = true; + + Assert.Equal(expectedEnabled, model.Enabled); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCitationConfig { Enabled = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCitationConfig { Enabled = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + bool expectedEnabled = true; + + Assert.Equal(expectedEnabled, deserialized.Enabled); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCitationConfig { Enabled = true }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationContentBlockLocationParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationContentBlockLocationParamTest.cs new file mode 100644 index 00000000..42d8a7d7 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationContentBlockLocationParamTest.cs @@ -0,0 +1,102 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCitationContentBlockLocationParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCitationContentBlockLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndBlockIndex = 0, + StartBlockIndex = 0, + }; + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "x"; + long expectedEndBlockIndex = 0; + long expectedStartBlockIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_location\"" + ); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedDocumentIndex, model.DocumentIndex); + Assert.Equal(expectedDocumentTitle, model.DocumentTitle); + Assert.Equal(expectedEndBlockIndex, model.EndBlockIndex); + Assert.Equal(expectedStartBlockIndex, model.StartBlockIndex); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCitationContentBlockLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndBlockIndex = 0, + StartBlockIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCitationContentBlockLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndBlockIndex = 0, + StartBlockIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "x"; + long expectedEndBlockIndex = 0; + long expectedStartBlockIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_location\"" + ); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedDocumentIndex, deserialized.DocumentIndex); + Assert.Equal(expectedDocumentTitle, deserialized.DocumentTitle); + Assert.Equal(expectedEndBlockIndex, deserialized.EndBlockIndex); + Assert.Equal(expectedStartBlockIndex, deserialized.StartBlockIndex); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCitationContentBlockLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndBlockIndex = 0, + StartBlockIndex = 0, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationContentBlockLocationTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationContentBlockLocationTest.cs new file mode 100644 index 00000000..64b58630 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationContentBlockLocationTest.cs @@ -0,0 +1,110 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCitationContentBlockLocationTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCitationContentBlockLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndBlockIndex = 0, + FileID = "file_id", + StartBlockIndex = 0, + }; + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "document_title"; + long expectedEndBlockIndex = 0; + string expectedFileID = "file_id"; + long expectedStartBlockIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_location\"" + ); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedDocumentIndex, model.DocumentIndex); + Assert.Equal(expectedDocumentTitle, model.DocumentTitle); + Assert.Equal(expectedEndBlockIndex, model.EndBlockIndex); + Assert.Equal(expectedFileID, model.FileID); + Assert.Equal(expectedStartBlockIndex, model.StartBlockIndex); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCitationContentBlockLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndBlockIndex = 0, + FileID = "file_id", + StartBlockIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCitationContentBlockLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndBlockIndex = 0, + FileID = "file_id", + StartBlockIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "document_title"; + long expectedEndBlockIndex = 0; + string expectedFileID = "file_id"; + long expectedStartBlockIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_location\"" + ); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedDocumentIndex, deserialized.DocumentIndex); + Assert.Equal(expectedDocumentTitle, deserialized.DocumentTitle); + Assert.Equal(expectedEndBlockIndex, deserialized.EndBlockIndex); + Assert.Equal(expectedFileID, deserialized.FileID); + Assert.Equal(expectedStartBlockIndex, deserialized.StartBlockIndex); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCitationContentBlockLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndBlockIndex = 0, + FileID = "file_id", + StartBlockIndex = 0, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationPageLocationParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationPageLocationParamTest.cs new file mode 100644 index 00000000..766d6997 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationPageLocationParamTest.cs @@ -0,0 +1,98 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCitationPageLocationParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCitationPageLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndPageNumber = 0, + StartPageNumber = 1, + }; + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "x"; + long expectedEndPageNumber = 0; + long expectedStartPageNumber = 1; + JsonElement expectedType = JsonSerializer.Deserialize("\"page_location\""); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedDocumentIndex, model.DocumentIndex); + Assert.Equal(expectedDocumentTitle, model.DocumentTitle); + Assert.Equal(expectedEndPageNumber, model.EndPageNumber); + Assert.Equal(expectedStartPageNumber, model.StartPageNumber); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCitationPageLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndPageNumber = 0, + StartPageNumber = 1, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCitationPageLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndPageNumber = 0, + StartPageNumber = 1, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "x"; + long expectedEndPageNumber = 0; + long expectedStartPageNumber = 1; + JsonElement expectedType = JsonSerializer.Deserialize("\"page_location\""); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedDocumentIndex, deserialized.DocumentIndex); + Assert.Equal(expectedDocumentTitle, deserialized.DocumentTitle); + Assert.Equal(expectedEndPageNumber, deserialized.EndPageNumber); + Assert.Equal(expectedStartPageNumber, deserialized.StartPageNumber); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCitationPageLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndPageNumber = 0, + StartPageNumber = 1, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationPageLocationTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationPageLocationTest.cs new file mode 100644 index 00000000..94aeb060 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationPageLocationTest.cs @@ -0,0 +1,106 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCitationPageLocationTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCitationPageLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndPageNumber = 0, + FileID = "file_id", + StartPageNumber = 1, + }; + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "document_title"; + long expectedEndPageNumber = 0; + string expectedFileID = "file_id"; + long expectedStartPageNumber = 1; + JsonElement expectedType = JsonSerializer.Deserialize("\"page_location\""); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedDocumentIndex, model.DocumentIndex); + Assert.Equal(expectedDocumentTitle, model.DocumentTitle); + Assert.Equal(expectedEndPageNumber, model.EndPageNumber); + Assert.Equal(expectedFileID, model.FileID); + Assert.Equal(expectedStartPageNumber, model.StartPageNumber); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCitationPageLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndPageNumber = 0, + FileID = "file_id", + StartPageNumber = 1, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCitationPageLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndPageNumber = 0, + FileID = "file_id", + StartPageNumber = 1, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "document_title"; + long expectedEndPageNumber = 0; + string expectedFileID = "file_id"; + long expectedStartPageNumber = 1; + JsonElement expectedType = JsonSerializer.Deserialize("\"page_location\""); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedDocumentIndex, deserialized.DocumentIndex); + Assert.Equal(expectedDocumentTitle, deserialized.DocumentTitle); + Assert.Equal(expectedEndPageNumber, deserialized.EndPageNumber); + Assert.Equal(expectedFileID, deserialized.FileID); + Assert.Equal(expectedStartPageNumber, deserialized.StartPageNumber); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCitationPageLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndPageNumber = 0, + FileID = "file_id", + StartPageNumber = 1, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationSearchResultLocationParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationSearchResultLocationParamTest.cs new file mode 100644 index 00000000..25d8aed1 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationSearchResultLocationParamTest.cs @@ -0,0 +1,110 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCitationSearchResultLocationParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCitationSearchResultLocationParam + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + string expectedCitedText = "cited_text"; + long expectedEndBlockIndex = 0; + long expectedSearchResultIndex = 0; + string expectedSource = "source"; + long expectedStartBlockIndex = 0; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"search_result_location\"" + ); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedEndBlockIndex, model.EndBlockIndex); + Assert.Equal(expectedSearchResultIndex, model.SearchResultIndex); + Assert.Equal(expectedSource, model.Source); + Assert.Equal(expectedStartBlockIndex, model.StartBlockIndex); + Assert.Equal(expectedTitle, model.Title); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCitationSearchResultLocationParam + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCitationSearchResultLocationParam + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedEndBlockIndex = 0; + long expectedSearchResultIndex = 0; + string expectedSource = "source"; + long expectedStartBlockIndex = 0; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"search_result_location\"" + ); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedEndBlockIndex, deserialized.EndBlockIndex); + Assert.Equal(expectedSearchResultIndex, deserialized.SearchResultIndex); + Assert.Equal(expectedSource, deserialized.Source); + Assert.Equal(expectedStartBlockIndex, deserialized.StartBlockIndex); + Assert.Equal(expectedTitle, deserialized.Title); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCitationSearchResultLocationParam + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationSearchResultLocationTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationSearchResultLocationTest.cs new file mode 100644 index 00000000..856c98c9 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationSearchResultLocationTest.cs @@ -0,0 +1,110 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCitationSearchResultLocationTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCitationSearchResultLocation + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + string expectedCitedText = "cited_text"; + long expectedEndBlockIndex = 0; + long expectedSearchResultIndex = 0; + string expectedSource = "source"; + long expectedStartBlockIndex = 0; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"search_result_location\"" + ); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedEndBlockIndex, model.EndBlockIndex); + Assert.Equal(expectedSearchResultIndex, model.SearchResultIndex); + Assert.Equal(expectedSource, model.Source); + Assert.Equal(expectedStartBlockIndex, model.StartBlockIndex); + Assert.Equal(expectedTitle, model.Title); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCitationSearchResultLocation + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCitationSearchResultLocation + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedEndBlockIndex = 0; + long expectedSearchResultIndex = 0; + string expectedSource = "source"; + long expectedStartBlockIndex = 0; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"search_result_location\"" + ); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedEndBlockIndex, deserialized.EndBlockIndex); + Assert.Equal(expectedSearchResultIndex, deserialized.SearchResultIndex); + Assert.Equal(expectedSource, deserialized.Source); + Assert.Equal(expectedStartBlockIndex, deserialized.StartBlockIndex); + Assert.Equal(expectedTitle, deserialized.Title); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCitationSearchResultLocation + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationWebSearchResultLocationParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationWebSearchResultLocationParamTest.cs new file mode 100644 index 00000000..c8ae4f3b --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationWebSearchResultLocationParamTest.cs @@ -0,0 +1,98 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCitationWebSearchResultLocationParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCitationWebSearchResultLocationParam + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "x", + URL = "x", + }; + + string expectedCitedText = "cited_text"; + string expectedEncryptedIndex = "encrypted_index"; + string expectedTitle = "x"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_result_location\"" + ); + string expectedURL = "x"; + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedEncryptedIndex, model.EncryptedIndex); + Assert.Equal(expectedTitle, model.Title); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedURL, model.URL); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCitationWebSearchResultLocationParam + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "x", + URL = "x", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCitationWebSearchResultLocationParam + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "x", + URL = "x", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + string expectedEncryptedIndex = "encrypted_index"; + string expectedTitle = "x"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_result_location\"" + ); + string expectedURL = "x"; + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedEncryptedIndex, deserialized.EncryptedIndex); + Assert.Equal(expectedTitle, deserialized.Title); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedURL, deserialized.URL); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCitationWebSearchResultLocationParam + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "x", + URL = "x", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationsConfigParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationsConfigParamTest.cs new file mode 100644 index 00000000..bdeddb20 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationsConfigParamTest.cs @@ -0,0 +1,92 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCitationsConfigParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCitationsConfigParam { Enabled = true }; + + bool expectedEnabled = true; + + Assert.Equal(expectedEnabled, model.Enabled); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCitationsConfigParam { Enabled = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCitationsConfigParam { Enabled = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + bool expectedEnabled = true; + + Assert.Equal(expectedEnabled, deserialized.Enabled); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCitationsConfigParam { Enabled = true }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaCitationsConfigParam { }; + + Assert.Null(model.Enabled); + Assert.False(model.RawData.ContainsKey("enabled")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaCitationsConfigParam { }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaCitationsConfigParam + { + // Null should be interpreted as omitted for these properties + Enabled = null, + }; + + Assert.Null(model.Enabled); + Assert.False(model.RawData.ContainsKey("enabled")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaCitationsConfigParam + { + // Null should be interpreted as omitted for these properties + Enabled = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationsDeltaTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationsDeltaTest.cs new file mode 100644 index 00000000..4eb4fd59 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationsDeltaTest.cs @@ -0,0 +1,114 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCitationsDeltaTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCitationsDelta + { + Citation = new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + }; + + Citation expectedCitation = new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"citations_delta\""); + + Assert.Equal(expectedCitation, model.Citation); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCitationsDelta + { + Citation = new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCitationsDelta + { + Citation = new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + Citation expectedCitation = new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"citations_delta\""); + + Assert.Equal(expectedCitation, deserialized.Citation); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCitationsDelta + { + Citation = new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationsWebSearchResultLocationTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationsWebSearchResultLocationTest.cs new file mode 100644 index 00000000..38ca8080 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCitationsWebSearchResultLocationTest.cs @@ -0,0 +1,94 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCitationsWebSearchResultLocationTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCitationsWebSearchResultLocation + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "title", + URL = "url", + }; + + string expectedCitedText = "cited_text"; + string expectedEncryptedIndex = "encrypted_index"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_result_location\"" + ); + string expectedURL = "url"; + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedEncryptedIndex, model.EncryptedIndex); + Assert.Equal(expectedTitle, model.Title); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedURL, model.URL); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCitationsWebSearchResultLocation + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "title", + URL = "url", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCitationsWebSearchResultLocation + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "title", + URL = "url", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + string expectedEncryptedIndex = "encrypted_index"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_result_location\"" + ); + string expectedURL = "url"; + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedEncryptedIndex, deserialized.EncryptedIndex); + Assert.Equal(expectedTitle, deserialized.Title); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedURL, deserialized.URL); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCitationsWebSearchResultLocation + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "title", + URL = "url", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaClearThinking20251015EditResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaClearThinking20251015EditResponseTest.cs new file mode 100644 index 00000000..5fe54909 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaClearThinking20251015EditResponseTest.cs @@ -0,0 +1,78 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaClearThinking20251015EditResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaClearThinking20251015EditResponse + { + ClearedInputTokens = 0, + ClearedThinkingTurns = 0, + }; + + long expectedClearedInputTokens = 0; + long expectedClearedThinkingTurns = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"clear_thinking_20251015\"" + ); + + Assert.Equal(expectedClearedInputTokens, model.ClearedInputTokens); + Assert.Equal(expectedClearedThinkingTurns, model.ClearedThinkingTurns); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaClearThinking20251015EditResponse + { + ClearedInputTokens = 0, + ClearedThinkingTurns = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaClearThinking20251015EditResponse + { + ClearedInputTokens = 0, + ClearedThinkingTurns = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedClearedInputTokens = 0; + long expectedClearedThinkingTurns = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"clear_thinking_20251015\"" + ); + + Assert.Equal(expectedClearedInputTokens, deserialized.ClearedInputTokens); + Assert.Equal(expectedClearedThinkingTurns, deserialized.ClearedThinkingTurns); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaClearThinking20251015EditResponse + { + ClearedInputTokens = 0, + ClearedThinkingTurns = 0, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaClearThinking20251015EditTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaClearThinking20251015EditTest.cs new file mode 100644 index 00000000..4e225650 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaClearThinking20251015EditTest.cs @@ -0,0 +1,163 @@ +using System.Text.Json; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaClearThinking20251015EditTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaClearThinking20251015Edit { Keep = new BetaThinkingTurns(1) }; + + JsonElement expectedType = JsonSerializer.Deserialize( + "\"clear_thinking_20251015\"" + ); + Keep expectedKeep = new BetaThinkingTurns(1); + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedKeep, model.Keep); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaClearThinking20251015Edit { Keep = new BetaThinkingTurns(1) }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaClearThinking20251015Edit { Keep = new BetaThinkingTurns(1) }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize( + "\"clear_thinking_20251015\"" + ); + Keep expectedKeep = new BetaThinkingTurns(1); + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedKeep, deserialized.Keep); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaClearThinking20251015Edit { Keep = new BetaThinkingTurns(1) }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaClearThinking20251015Edit { }; + + Assert.Null(model.Keep); + Assert.False(model.RawData.ContainsKey("keep")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaClearThinking20251015Edit { }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaClearThinking20251015Edit + { + // Null should be interpreted as omitted for these properties + Keep = null, + }; + + Assert.Null(model.Keep); + Assert.False(model.RawData.ContainsKey("keep")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaClearThinking20251015Edit + { + // Null should be interpreted as omitted for these properties + Keep = null, + }; + + model.Validate(); + } +} + +public class UnionMember2Test : TestBase +{ + [Fact] + public void DefaultValidation_Works() + { + var constant = new UnionMember2(); + constant.Validate(); + } + + [Fact] + public void ValidConstantValidation_Works() + { + var constant = JsonSerializer.Deserialize( + JsonSerializer.Deserialize("\"all\"") + ); + constant.Validate(); + } + + [Fact] + public void InvalidConstantValidationThrows_Works() + { + var constant = JsonSerializer.Deserialize( + JsonSerializer.Deserialize("\"invalid value\"") + ); + Assert.Throws(() => constant.Validate()); + } + + [Fact] + public void DefaultRoundtrip_Works() + { + var constant = new UnionMember2(); + var json = JsonSerializer.Serialize(constant); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(constant, deserialized); + } + + [Fact] + public void ValidConstantRoundtrip_Works() + { + var constant = JsonSerializer.Deserialize( + JsonSerializer.Deserialize("\"all\"") + ); + var json = JsonSerializer.Serialize(constant); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(constant, deserialized); + } + + [Fact] + public void InvalidConstantRoundtrip_Works() + { + var constant = JsonSerializer.Deserialize( + JsonSerializer.Deserialize("\"invalid value\"") + ); + var json = JsonSerializer.Serialize(constant); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(constant, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaClearToolUses20250919EditResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaClearToolUses20250919EditResponseTest.cs new file mode 100644 index 00000000..946a4b70 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaClearToolUses20250919EditResponseTest.cs @@ -0,0 +1,78 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaClearToolUses20250919EditResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaClearToolUses20250919EditResponse + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }; + + long expectedClearedInputTokens = 0; + long expectedClearedToolUses = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"clear_tool_uses_20250919\"" + ); + + Assert.Equal(expectedClearedInputTokens, model.ClearedInputTokens); + Assert.Equal(expectedClearedToolUses, model.ClearedToolUses); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaClearToolUses20250919EditResponse + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaClearToolUses20250919EditResponse + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedClearedInputTokens = 0; + long expectedClearedToolUses = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"clear_tool_uses_20250919\"" + ); + + Assert.Equal(expectedClearedInputTokens, deserialized.ClearedInputTokens); + Assert.Equal(expectedClearedToolUses, deserialized.ClearedToolUses); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaClearToolUses20250919EditResponse + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaClearToolUses20250919EditTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaClearToolUses20250919EditTest.cs new file mode 100644 index 00000000..4e71881d --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaClearToolUses20250919EditTest.cs @@ -0,0 +1,243 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaClearToolUses20250919EditTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaClearToolUses20250919Edit + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new BetaInputTokensTrigger(1), + }; + + JsonElement expectedType = JsonSerializer.Deserialize( + "\"clear_tool_uses_20250919\"" + ); + BetaInputTokensClearAtLeast expectedClearAtLeast = new(0); + ClearToolInputs expectedClearToolInputs = true; + List expectedExcludeTools = ["string"]; + BetaToolUsesKeep expectedKeep = new(0); + Trigger expectedTrigger = new BetaInputTokensTrigger(1); + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedClearAtLeast, model.ClearAtLeast); + Assert.Equal(expectedClearToolInputs, model.ClearToolInputs); + Assert.Equal(expectedExcludeTools.Count, model.ExcludeTools.Count); + for (int i = 0; i < expectedExcludeTools.Count; i++) + { + Assert.Equal(expectedExcludeTools[i], model.ExcludeTools[i]); + } + Assert.Equal(expectedKeep, model.Keep); + Assert.Equal(expectedTrigger, model.Trigger); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaClearToolUses20250919Edit + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new BetaInputTokensTrigger(1), + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaClearToolUses20250919Edit + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new BetaInputTokensTrigger(1), + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize( + "\"clear_tool_uses_20250919\"" + ); + BetaInputTokensClearAtLeast expectedClearAtLeast = new(0); + ClearToolInputs expectedClearToolInputs = true; + List expectedExcludeTools = ["string"]; + BetaToolUsesKeep expectedKeep = new(0); + Trigger expectedTrigger = new BetaInputTokensTrigger(1); + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedClearAtLeast, deserialized.ClearAtLeast); + Assert.Equal(expectedClearToolInputs, deserialized.ClearToolInputs); + Assert.Equal(expectedExcludeTools.Count, deserialized.ExcludeTools.Count); + for (int i = 0; i < expectedExcludeTools.Count; i++) + { + Assert.Equal(expectedExcludeTools[i], deserialized.ExcludeTools[i]); + } + Assert.Equal(expectedKeep, deserialized.Keep); + Assert.Equal(expectedTrigger, deserialized.Trigger); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaClearToolUses20250919Edit + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new BetaInputTokensTrigger(1), + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaClearToolUses20250919Edit + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + }; + + Assert.Null(model.Keep); + Assert.False(model.RawData.ContainsKey("keep")); + Assert.Null(model.Trigger); + Assert.False(model.RawData.ContainsKey("trigger")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaClearToolUses20250919Edit + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaClearToolUses20250919Edit + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + + // Null should be interpreted as omitted for these properties + Keep = null, + Trigger = null, + }; + + Assert.Null(model.Keep); + Assert.False(model.RawData.ContainsKey("keep")); + Assert.Null(model.Trigger); + Assert.False(model.RawData.ContainsKey("trigger")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaClearToolUses20250919Edit + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + + // Null should be interpreted as omitted for these properties + Keep = null, + Trigger = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaClearToolUses20250919Edit + { + Keep = new(0), + Trigger = new BetaInputTokensTrigger(1), + }; + + Assert.Null(model.ClearAtLeast); + Assert.False(model.RawData.ContainsKey("clear_at_least")); + Assert.Null(model.ClearToolInputs); + Assert.False(model.RawData.ContainsKey("clear_tool_inputs")); + Assert.Null(model.ExcludeTools); + Assert.False(model.RawData.ContainsKey("exclude_tools")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaClearToolUses20250919Edit + { + Keep = new(0), + Trigger = new BetaInputTokensTrigger(1), + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaClearToolUses20250919Edit + { + Keep = new(0), + Trigger = new BetaInputTokensTrigger(1), + + ClearAtLeast = null, + ClearToolInputs = null, + ExcludeTools = null, + }; + + Assert.Null(model.ClearAtLeast); + Assert.True(model.RawData.ContainsKey("clear_at_least")); + Assert.Null(model.ClearToolInputs); + Assert.True(model.RawData.ContainsKey("clear_tool_inputs")); + Assert.Null(model.ExcludeTools); + Assert.True(model.RawData.ContainsKey("exclude_tools")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaClearToolUses20250919Edit + { + Keep = new(0), + Trigger = new BetaInputTokensTrigger(1), + + ClearAtLeast = null, + ClearToolInputs = null, + ExcludeTools = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionOutputBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionOutputBlockParamTest.cs new file mode 100644 index 00000000..0fd093b5 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionOutputBlockParamTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCodeExecutionOutputBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCodeExecutionOutputBlockParam { FileID = "file_id" }; + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_output\"" + ); + + Assert.Equal(expectedFileID, model.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCodeExecutionOutputBlockParam { FileID = "file_id" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCodeExecutionOutputBlockParam { FileID = "file_id" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_output\"" + ); + + Assert.Equal(expectedFileID, deserialized.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCodeExecutionOutputBlockParam { FileID = "file_id" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionOutputBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionOutputBlockTest.cs new file mode 100644 index 00000000..ca1cc98c --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionOutputBlockTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCodeExecutionOutputBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCodeExecutionOutputBlock { FileID = "file_id" }; + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_output\"" + ); + + Assert.Equal(expectedFileID, model.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCodeExecutionOutputBlock { FileID = "file_id" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCodeExecutionOutputBlock { FileID = "file_id" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_output\"" + ); + + Assert.Equal(expectedFileID, deserialized.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCodeExecutionOutputBlock { FileID = "file_id" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionResultBlockParamTest.cs new file mode 100644 index 00000000..5fecf403 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionResultBlockParamTest.cs @@ -0,0 +1,103 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCodeExecutionResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCodeExecutionResultBlockParam + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + List expectedContent = [new("file_id")]; + long expectedReturnCode = 0; + string expectedStderr = "stderr"; + string expectedStdout = "stdout"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_result\"" + ); + + Assert.Equal(expectedContent.Count, model.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], model.Content[i]); + } + Assert.Equal(expectedReturnCode, model.ReturnCode); + Assert.Equal(expectedStderr, model.Stderr); + Assert.Equal(expectedStdout, model.Stdout); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCodeExecutionResultBlockParam + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCodeExecutionResultBlockParam + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedContent = [new("file_id")]; + long expectedReturnCode = 0; + string expectedStderr = "stderr"; + string expectedStdout = "stdout"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_result\"" + ); + + Assert.Equal(expectedContent.Count, deserialized.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], deserialized.Content[i]); + } + Assert.Equal(expectedReturnCode, deserialized.ReturnCode); + Assert.Equal(expectedStderr, deserialized.Stderr); + Assert.Equal(expectedStdout, deserialized.Stdout); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCodeExecutionResultBlockParam + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionResultBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionResultBlockTest.cs new file mode 100644 index 00000000..de5e4296 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionResultBlockTest.cs @@ -0,0 +1,103 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCodeExecutionResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCodeExecutionResultBlock + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + List expectedContent = [new("file_id")]; + long expectedReturnCode = 0; + string expectedStderr = "stderr"; + string expectedStdout = "stdout"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_result\"" + ); + + Assert.Equal(expectedContent.Count, model.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], model.Content[i]); + } + Assert.Equal(expectedReturnCode, model.ReturnCode); + Assert.Equal(expectedStderr, model.Stderr); + Assert.Equal(expectedStdout, model.Stdout); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCodeExecutionResultBlock + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCodeExecutionResultBlock + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedContent = [new("file_id")]; + long expectedReturnCode = 0; + string expectedStderr = "stderr"; + string expectedStdout = "stdout"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_result\"" + ); + + Assert.Equal(expectedContent.Count, deserialized.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], deserialized.Content[i]); + } + Assert.Equal(expectedReturnCode, deserialized.ReturnCode); + Assert.Equal(expectedStderr, deserialized.Stderr); + Assert.Equal(expectedStdout, deserialized.Stdout); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCodeExecutionResultBlock + { + Content = [new("file_id")], + ReturnCode = 0, + Stderr = "stderr", + Stdout = "stdout", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionTool20250522Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionTool20250522Test.cs new file mode 100644 index 00000000..af717880 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionTool20250522Test.cs @@ -0,0 +1,281 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCodeExecutionTool20250522Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCodeExecutionTool20250522 + { + AllowedCallers = [AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + JsonElement expectedName = JsonSerializer.Deserialize("\"code_execution\""); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_20250522\"" + ); + List> expectedAllowedCallers = [AllowedCaller.Direct]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedStrict, model.Strict); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCodeExecutionTool20250522 + { + AllowedCallers = [AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCodeExecutionTool20250522 + { + AllowedCallers = [AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize("\"code_execution\""); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_20250522\"" + ); + List> expectedAllowedCallers = [AllowedCaller.Direct]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedStrict, deserialized.Strict); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCodeExecutionTool20250522 + { + AllowedCallers = [AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaCodeExecutionTool20250522 { CacheControl = new() { TTL = TTL.TTL5m } }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaCodeExecutionTool20250522 { CacheControl = new() { TTL = TTL.TTL5m } }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaCodeExecutionTool20250522 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaCodeExecutionTool20250522 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaCodeExecutionTool20250522 + { + AllowedCallers = [AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaCodeExecutionTool20250522 + { + AllowedCallers = [AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaCodeExecutionTool20250522 + { + AllowedCallers = [AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaCodeExecutionTool20250522 + { + AllowedCallers = [AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + + CacheControl = null, + }; + + model.Validate(); + } +} + +public class AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(AllowedCaller.Direct)] + [InlineData(AllowedCaller.CodeExecution20250825)] + public void Validation_Works(AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(AllowedCaller.Direct)] + [InlineData(AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionTool20250825Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionTool20250825Test.cs new file mode 100644 index 00000000..141d38b0 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionTool20250825Test.cs @@ -0,0 +1,289 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCodeExecutionTool20250825Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCodeExecutionTool20250825 + { + AllowedCallers = [BetaCodeExecutionTool20250825AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + JsonElement expectedName = JsonSerializer.Deserialize("\"code_execution\""); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_20250825\"" + ); + List> expectedAllowedCallers = + [ + BetaCodeExecutionTool20250825AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedStrict, model.Strict); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCodeExecutionTool20250825 + { + AllowedCallers = [BetaCodeExecutionTool20250825AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCodeExecutionTool20250825 + { + AllowedCallers = [BetaCodeExecutionTool20250825AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize("\"code_execution\""); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_20250825\"" + ); + List> expectedAllowedCallers = + [ + BetaCodeExecutionTool20250825AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedStrict, deserialized.Strict); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCodeExecutionTool20250825 + { + AllowedCallers = [BetaCodeExecutionTool20250825AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaCodeExecutionTool20250825 { CacheControl = new() { TTL = TTL.TTL5m } }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaCodeExecutionTool20250825 { CacheControl = new() { TTL = TTL.TTL5m } }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaCodeExecutionTool20250825 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaCodeExecutionTool20250825 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaCodeExecutionTool20250825 + { + AllowedCallers = [BetaCodeExecutionTool20250825AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaCodeExecutionTool20250825 + { + AllowedCallers = [BetaCodeExecutionTool20250825AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaCodeExecutionTool20250825 + { + AllowedCallers = [BetaCodeExecutionTool20250825AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaCodeExecutionTool20250825 + { + AllowedCallers = [BetaCodeExecutionTool20250825AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + + CacheControl = null, + }; + + model.Validate(); + } +} + +public class BetaCodeExecutionTool20250825AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaCodeExecutionTool20250825AllowedCaller.Direct)] + [InlineData(BetaCodeExecutionTool20250825AllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaCodeExecutionTool20250825AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaCodeExecutionTool20250825AllowedCaller.Direct)] + [InlineData(BetaCodeExecutionTool20250825AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaCodeExecutionTool20250825AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultBlockContentTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultBlockContentTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultBlockContentTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultBlockParamContentTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultBlockParamContentTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultBlockParamContentTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultBlockParamTest.cs new file mode 100644 index 00000000..ad766459 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultBlockParamTest.cs @@ -0,0 +1,162 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCodeExecutionToolResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCodeExecutionToolResultBlockParam + { + Content = new BetaCodeExecutionToolResultErrorParam( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + BetaCodeExecutionToolResultBlockParamContent expectedContent = + new BetaCodeExecutionToolResultErrorParam( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_tool_result\"" + ); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCodeExecutionToolResultBlockParam + { + Content = new BetaCodeExecutionToolResultErrorParam( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCodeExecutionToolResultBlockParam + { + Content = new BetaCodeExecutionToolResultErrorParam( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaCodeExecutionToolResultBlockParamContent expectedContent = + new BetaCodeExecutionToolResultErrorParam( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_tool_result\"" + ); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCodeExecutionToolResultBlockParam + { + Content = new BetaCodeExecutionToolResultErrorParam( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaCodeExecutionToolResultBlockParam + { + Content = new BetaCodeExecutionToolResultErrorParam( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaCodeExecutionToolResultBlockParam + { + Content = new BetaCodeExecutionToolResultErrorParam( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaCodeExecutionToolResultBlockParam + { + Content = new BetaCodeExecutionToolResultErrorParam( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaCodeExecutionToolResultBlockParam + { + Content = new BetaCodeExecutionToolResultErrorParam( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultBlockTest.cs new file mode 100644 index 00000000..8a0efaf3 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultBlockTest.cs @@ -0,0 +1,92 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCodeExecutionToolResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCodeExecutionToolResultBlock + { + Content = new BetaCodeExecutionToolResultError( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + BetaCodeExecutionToolResultBlockContent expectedContent = + new BetaCodeExecutionToolResultError( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_tool_result\"" + ); + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCodeExecutionToolResultBlock + { + Content = new BetaCodeExecutionToolResultError( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCodeExecutionToolResultBlock + { + Content = new BetaCodeExecutionToolResultError( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaCodeExecutionToolResultBlockContent expectedContent = + new BetaCodeExecutionToolResultError( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_tool_result\"" + ); + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCodeExecutionToolResultBlock + { + Content = new BetaCodeExecutionToolResultError( + BetaCodeExecutionToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultErrorCodeTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultErrorCodeTest.cs new file mode 100644 index 00000000..ad76081d --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultErrorCodeTest.cs @@ -0,0 +1,68 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCodeExecutionToolResultErrorCodeTest : TestBase +{ + [Theory] + [InlineData(BetaCodeExecutionToolResultErrorCode.InvalidToolInput)] + [InlineData(BetaCodeExecutionToolResultErrorCode.Unavailable)] + [InlineData(BetaCodeExecutionToolResultErrorCode.TooManyRequests)] + [InlineData(BetaCodeExecutionToolResultErrorCode.ExecutionTimeExceeded)] + public void Validation_Works(BetaCodeExecutionToolResultErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaCodeExecutionToolResultErrorCode.InvalidToolInput)] + [InlineData(BetaCodeExecutionToolResultErrorCode.Unavailable)] + [InlineData(BetaCodeExecutionToolResultErrorCode.TooManyRequests)] + [InlineData(BetaCodeExecutionToolResultErrorCode.ExecutionTimeExceeded)] + public void SerializationRoundtrip_Works(BetaCodeExecutionToolResultErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultErrorParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultErrorParamTest.cs new file mode 100644 index 00000000..f39947b8 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultErrorParamTest.cs @@ -0,0 +1,73 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCodeExecutionToolResultErrorParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCodeExecutionToolResultErrorParam + { + ErrorCode = BetaCodeExecutionToolResultErrorCode.InvalidToolInput, + }; + + ApiEnum expectedErrorCode = + BetaCodeExecutionToolResultErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, model.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCodeExecutionToolResultErrorParam + { + ErrorCode = BetaCodeExecutionToolResultErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCodeExecutionToolResultErrorParam + { + ErrorCode = BetaCodeExecutionToolResultErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ApiEnum expectedErrorCode = + BetaCodeExecutionToolResultErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, deserialized.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCodeExecutionToolResultErrorParam + { + ErrorCode = BetaCodeExecutionToolResultErrorCode.InvalidToolInput, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultErrorTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultErrorTest.cs new file mode 100644 index 00000000..0179474e --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCodeExecutionToolResultErrorTest.cs @@ -0,0 +1,73 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCodeExecutionToolResultErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCodeExecutionToolResultError + { + ErrorCode = BetaCodeExecutionToolResultErrorCode.InvalidToolInput, + }; + + ApiEnum expectedErrorCode = + BetaCodeExecutionToolResultErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, model.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCodeExecutionToolResultError + { + ErrorCode = BetaCodeExecutionToolResultErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCodeExecutionToolResultError + { + ErrorCode = BetaCodeExecutionToolResultErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ApiEnum expectedErrorCode = + BetaCodeExecutionToolResultErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, deserialized.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCodeExecutionToolResultError + { + ErrorCode = BetaCodeExecutionToolResultErrorCode.InvalidToolInput, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaContainerParamsTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaContainerParamsTest.cs new file mode 100644 index 00000000..89036886 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaContainerParamsTest.cs @@ -0,0 +1,165 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaContainerParamsTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaContainerParams + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }; + + string expectedID = "id"; + List expectedSkills = + [ + new() + { + SkillID = "x", + Type = BetaSkillParamsType.Anthropic, + Version = "x", + }, + ]; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedSkills.Count, model.Skills.Count); + for (int i = 0; i < expectedSkills.Count; i++) + { + Assert.Equal(expectedSkills[i], model.Skills[i]); + } + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaContainerParams + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaContainerParams + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "id"; + List expectedSkills = + [ + new() + { + SkillID = "x", + Type = BetaSkillParamsType.Anthropic, + Version = "x", + }, + ]; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedSkills.Count, deserialized.Skills.Count); + for (int i = 0; i < expectedSkills.Count; i++) + { + Assert.Equal(expectedSkills[i], deserialized.Skills[i]); + } + } + + [Fact] + public void Validation_Works() + { + var model = new BetaContainerParams + { + ID = "id", + Skills = + [ + new() + { + SkillID = "x", + Type = BetaSkillParamsType.Anthropic, + Version = "x", + }, + ], + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaContainerParams { }; + + Assert.Null(model.ID); + Assert.False(model.RawData.ContainsKey("id")); + Assert.Null(model.Skills); + Assert.False(model.RawData.ContainsKey("skills")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaContainerParams { }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaContainerParams { ID = null, Skills = null }; + + Assert.Null(model.ID); + Assert.True(model.RawData.ContainsKey("id")); + Assert.Null(model.Skills); + Assert.True(model.RawData.ContainsKey("skills")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaContainerParams { ID = null, Skills = null }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaContainerTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaContainerTest.cs new file mode 100644 index 00000000..25da3e19 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaContainerTest.cs @@ -0,0 +1,136 @@ +using System; +using System.Collections.Generic; +using System.Text.Json; +using Messages = Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaContainerTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Messages::BetaContainer + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }; + + string expectedID = "id"; + DateTimeOffset expectedExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"); + List expectedSkills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ]; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedExpiresAt, model.ExpiresAt); + Assert.Equal(expectedSkills.Count, model.Skills.Count); + for (int i = 0; i < expectedSkills.Count; i++) + { + Assert.Equal(expectedSkills[i], model.Skills[i]); + } + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Messages::BetaContainer + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Messages::BetaContainer + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "id"; + DateTimeOffset expectedExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"); + List expectedSkills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ]; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedExpiresAt, deserialized.ExpiresAt); + Assert.Equal(expectedSkills.Count, deserialized.Skills.Count); + for (int i = 0; i < expectedSkills.Count; i++) + { + Assert.Equal(expectedSkills[i], deserialized.Skills[i]); + } + } + + [Fact] + public void Validation_Works() + { + var model = new Messages::BetaContainer + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaContainerUploadBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaContainerUploadBlockParamTest.cs new file mode 100644 index 00000000..1fa0aa4f --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaContainerUploadBlockParamTest.cs @@ -0,0 +1,118 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaContainerUploadBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaContainerUploadBlockParam + { + FileID = "file_id", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"container_upload\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedFileID, model.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaContainerUploadBlockParam + { + FileID = "file_id", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaContainerUploadBlockParam + { + FileID = "file_id", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"container_upload\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedFileID, deserialized.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaContainerUploadBlockParam + { + FileID = "file_id", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaContainerUploadBlockParam { FileID = "file_id" }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaContainerUploadBlockParam { FileID = "file_id" }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaContainerUploadBlockParam + { + FileID = "file_id", + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaContainerUploadBlockParam + { + FileID = "file_id", + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaContainerUploadBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaContainerUploadBlockTest.cs new file mode 100644 index 00000000..4f5bb4f9 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaContainerUploadBlockTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaContainerUploadBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaContainerUploadBlock { FileID = "file_id" }; + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"container_upload\""); + + Assert.Equal(expectedFileID, model.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaContainerUploadBlock { FileID = "file_id" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaContainerUploadBlock { FileID = "file_id" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"container_upload\""); + + Assert.Equal(expectedFileID, deserialized.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaContainerUploadBlock { FileID = "file_id" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaContentBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaContentBlockParamTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaContentBlockParamTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaContentBlockSourceTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaContentBlockSourceTest.cs new file mode 100644 index 00000000..faa5ad41 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaContentBlockSourceTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaContentBlockSourceTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaContentBlockSource { Content = "string" }; + + BetaContentBlockSourceContent expectedContent = "string"; + JsonElement expectedType = JsonSerializer.Deserialize("\"content\""); + + Assert.Equal(expectedContent, model.Content); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaContentBlockSource { Content = "string" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaContentBlockSource { Content = "string" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaContentBlockSourceContent expectedContent = "string"; + JsonElement expectedType = JsonSerializer.Deserialize("\"content\""); + + Assert.Equal(expectedContent, deserialized.Content); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaContentBlockSource { Content = "string" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaContentBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaContentBlockTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaContentBlockTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaContextManagementConfigTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaContextManagementConfigTest.cs new file mode 100644 index 00000000..ab927f50 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaContextManagementConfigTest.cs @@ -0,0 +1,173 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaContextManagementConfigTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaContextManagementConfig + { + Edits = + [ + new BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new BetaInputTokensTrigger(1), + }, + ], + }; + + List expectedEdits = + [ + new BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new BetaInputTokensTrigger(1), + }, + ]; + + Assert.Equal(expectedEdits.Count, model.Edits.Count); + for (int i = 0; i < expectedEdits.Count; i++) + { + Assert.Equal(expectedEdits[i], model.Edits[i]); + } + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaContextManagementConfig + { + Edits = + [ + new BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new BetaInputTokensTrigger(1), + }, + ], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaContextManagementConfig + { + Edits = + [ + new BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new BetaInputTokensTrigger(1), + }, + ], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedEdits = + [ + new BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new BetaInputTokensTrigger(1), + }, + ]; + + Assert.Equal(expectedEdits.Count, deserialized.Edits.Count); + for (int i = 0; i < expectedEdits.Count; i++) + { + Assert.Equal(expectedEdits[i], deserialized.Edits[i]); + } + } + + [Fact] + public void Validation_Works() + { + var model = new BetaContextManagementConfig + { + Edits = + [ + new BetaClearToolUses20250919Edit() + { + ClearAtLeast = new(0), + ClearToolInputs = true, + ExcludeTools = ["string"], + Keep = new(0), + Trigger = new BetaInputTokensTrigger(1), + }, + ], + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaContextManagementConfig { }; + + Assert.Null(model.Edits); + Assert.False(model.RawData.ContainsKey("edits")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaContextManagementConfig { }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaContextManagementConfig + { + // Null should be interpreted as omitted for these properties + Edits = null, + }; + + Assert.Null(model.Edits); + Assert.False(model.RawData.ContainsKey("edits")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaContextManagementConfig + { + // Null should be interpreted as omitted for these properties + Edits = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaContextManagementResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaContextManagementResponseTest.cs new file mode 100644 index 00000000..3fb7fe10 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaContextManagementResponseTest.cs @@ -0,0 +1,113 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaContextManagementResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaContextManagementResponse + { + AppliedEdits = + [ + new BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ], + }; + + List expectedAppliedEdits = + [ + new BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ]; + + Assert.Equal(expectedAppliedEdits.Count, model.AppliedEdits.Count); + for (int i = 0; i < expectedAppliedEdits.Count; i++) + { + Assert.Equal(expectedAppliedEdits[i], model.AppliedEdits[i]); + } + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaContextManagementResponse + { + AppliedEdits = + [ + new BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaContextManagementResponse + { + AppliedEdits = + [ + new BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedAppliedEdits = + [ + new BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ]; + + Assert.Equal(expectedAppliedEdits.Count, deserialized.AppliedEdits.Count); + for (int i = 0; i < expectedAppliedEdits.Count; i++) + { + Assert.Equal(expectedAppliedEdits[i], deserialized.AppliedEdits[i]); + } + } + + [Fact] + public void Validation_Works() + { + var model = new BetaContextManagementResponse + { + AppliedEdits = + [ + new BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ], + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaCountTokensContextManagementResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaCountTokensContextManagementResponseTest.cs new file mode 100644 index 00000000..c90d8c16 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaCountTokensContextManagementResponseTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaCountTokensContextManagementResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaCountTokensContextManagementResponse { OriginalInputTokens = 0 }; + + long expectedOriginalInputTokens = 0; + + Assert.Equal(expectedOriginalInputTokens, model.OriginalInputTokens); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaCountTokensContextManagementResponse { OriginalInputTokens = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaCountTokensContextManagementResponse { OriginalInputTokens = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + Assert.NotNull(deserialized); + + long expectedOriginalInputTokens = 0; + + Assert.Equal(expectedOriginalInputTokens, deserialized.OriginalInputTokens); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaCountTokensContextManagementResponse { OriginalInputTokens = 0 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaDirectCallerTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaDirectCallerTest.cs new file mode 100644 index 00000000..82de408a --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaDirectCallerTest.cs @@ -0,0 +1,50 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaDirectCallerTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaDirectCaller { }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"direct\""); + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaDirectCaller { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaDirectCaller { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"direct\""); + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaDirectCaller { }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaDocumentBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaDocumentBlockTest.cs new file mode 100644 index 00000000..a9936a4e --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaDocumentBlockTest.cs @@ -0,0 +1,82 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaDocumentBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaDocumentBlock + { + Citations = new(true), + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + Title = "title", + }; + + BetaCitationConfig expectedCitations = new(true); + Source expectedSource = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"); + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize("\"document\""); + + Assert.Equal(expectedCitations, model.Citations); + Assert.Equal(expectedSource, model.Source); + Assert.Equal(expectedTitle, model.Title); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaDocumentBlock + { + Citations = new(true), + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + Title = "title", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaDocumentBlock + { + Citations = new(true), + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + Title = "title", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaCitationConfig expectedCitations = new(true); + Source expectedSource = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"); + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize("\"document\""); + + Assert.Equal(expectedCitations, deserialized.Citations); + Assert.Equal(expectedSource, deserialized.Source); + Assert.Equal(expectedTitle, deserialized.Title); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaDocumentBlock + { + Citations = new(true), + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + Title = "title", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaFileDocumentSourceTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaFileDocumentSourceTest.cs new file mode 100644 index 00000000..6a837179 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaFileDocumentSourceTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaFileDocumentSourceTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaFileDocumentSource { FileID = "file_id" }; + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"file\""); + + Assert.Equal(expectedFileID, model.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaFileDocumentSource { FileID = "file_id" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaFileDocumentSource { FileID = "file_id" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"file\""); + + Assert.Equal(expectedFileID, deserialized.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaFileDocumentSource { FileID = "file_id" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaFileImageSourceTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaFileImageSourceTest.cs new file mode 100644 index 00000000..ba59acc4 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaFileImageSourceTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaFileImageSourceTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaFileImageSource { FileID = "file_id" }; + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"file\""); + + Assert.Equal(expectedFileID, model.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaFileImageSource { FileID = "file_id" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaFileImageSource { FileID = "file_id" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedFileID = "file_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"file\""); + + Assert.Equal(expectedFileID, deserialized.FileID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaFileImageSource { FileID = "file_id" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaImageBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaImageBlockParamTest.cs new file mode 100644 index 00000000..12758f7b --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaImageBlockParamTest.cs @@ -0,0 +1,164 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaImageBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaImageBlockParam + { + Source = new BetaBase64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + BetaImageBlockParamSource expectedSource = new BetaBase64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"image\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedSource, model.Source); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaImageBlockParam + { + Source = new BetaBase64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaImageBlockParam + { + Source = new BetaBase64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaImageBlockParamSource expectedSource = new BetaBase64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"image\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedSource, deserialized.Source); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaImageBlockParam + { + Source = new BetaBase64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaImageBlockParam + { + Source = new BetaBase64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaImageBlockParam + { + Source = new BetaBase64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaImageBlockParam + { + Source = new BetaBase64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaImageBlockParam + { + Source = new BetaBase64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaInputJSONDeltaTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaInputJSONDeltaTest.cs new file mode 100644 index 00000000..fd5c0d50 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaInputJSONDeltaTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaInputJSONDeltaTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaInputJSONDelta { PartialJSON = "partial_json" }; + + string expectedPartialJSON = "partial_json"; + JsonElement expectedType = JsonSerializer.Deserialize("\"input_json_delta\""); + + Assert.Equal(expectedPartialJSON, model.PartialJSON); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaInputJSONDelta { PartialJSON = "partial_json" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaInputJSONDelta { PartialJSON = "partial_json" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedPartialJSON = "partial_json"; + JsonElement expectedType = JsonSerializer.Deserialize("\"input_json_delta\""); + + Assert.Equal(expectedPartialJSON, deserialized.PartialJSON); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaInputJSONDelta { PartialJSON = "partial_json" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaInputTokensClearAtLeastTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaInputTokensClearAtLeastTest.cs new file mode 100644 index 00000000..8de939ec --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaInputTokensClearAtLeastTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaInputTokensClearAtLeastTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaInputTokensClearAtLeast { Value = 0 }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"input_tokens\""); + long expectedValue = 0; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedValue, model.Value); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaInputTokensClearAtLeast { Value = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaInputTokensClearAtLeast { Value = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"input_tokens\""); + long expectedValue = 0; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedValue, deserialized.Value); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaInputTokensClearAtLeast { Value = 0 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaInputTokensTriggerTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaInputTokensTriggerTest.cs new file mode 100644 index 00000000..8bce826d --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaInputTokensTriggerTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaInputTokensTriggerTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaInputTokensTrigger { Value = 1 }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"input_tokens\""); + long expectedValue = 1; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedValue, model.Value); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaInputTokensTrigger { Value = 1 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaInputTokensTrigger { Value = 1 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"input_tokens\""); + long expectedValue = 1; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedValue, deserialized.Value); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaInputTokensTrigger { Value = 1 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaJSONOutputFormatTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaJSONOutputFormatTest.cs new file mode 100644 index 00000000..3e63a460 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaJSONOutputFormatTest.cs @@ -0,0 +1,97 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaJSONOutputFormatTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaJSONOutputFormat + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }; + + Dictionary expectedSchema = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"json_schema\""); + + Assert.Equal(expectedSchema.Count, model.Schema.Count); + foreach (var item in expectedSchema) + { + Assert.True(model.Schema.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.Schema[item.Key])); + } + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaJSONOutputFormat + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaJSONOutputFormat + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + Dictionary expectedSchema = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"json_schema\""); + + Assert.Equal(expectedSchema.Count, deserialized.Schema.Count); + foreach (var item in expectedSchema) + { + Assert.True(deserialized.Schema.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.Schema[item.Key])); + } + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaJSONOutputFormat + { + Schema = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolConfigTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolConfigTest.cs new file mode 100644 index 00000000..1beb3094 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolConfigTest.cs @@ -0,0 +1,102 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMCPToolConfigTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMCPToolConfig { DeferLoading = true, Enabled = true }; + + bool expectedDeferLoading = true; + bool expectedEnabled = true; + + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedEnabled, model.Enabled); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMCPToolConfig { DeferLoading = true, Enabled = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMCPToolConfig { DeferLoading = true, Enabled = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + bool expectedDeferLoading = true; + bool expectedEnabled = true; + + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedEnabled, deserialized.Enabled); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMCPToolConfig { DeferLoading = true, Enabled = true }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaMCPToolConfig { }; + + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Enabled); + Assert.False(model.RawData.ContainsKey("enabled")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaMCPToolConfig { }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaMCPToolConfig + { + // Null should be interpreted as omitted for these properties + DeferLoading = null, + Enabled = null, + }; + + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Enabled); + Assert.False(model.RawData.ContainsKey("enabled")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaMCPToolConfig + { + // Null should be interpreted as omitted for these properties + DeferLoading = null, + Enabled = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolDefaultConfigTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolDefaultConfigTest.cs new file mode 100644 index 00000000..5321fede --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolDefaultConfigTest.cs @@ -0,0 +1,102 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMCPToolDefaultConfigTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMCPToolDefaultConfig { DeferLoading = true, Enabled = true }; + + bool expectedDeferLoading = true; + bool expectedEnabled = true; + + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedEnabled, model.Enabled); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMCPToolDefaultConfig { DeferLoading = true, Enabled = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMCPToolDefaultConfig { DeferLoading = true, Enabled = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + bool expectedDeferLoading = true; + bool expectedEnabled = true; + + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedEnabled, deserialized.Enabled); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMCPToolDefaultConfig { DeferLoading = true, Enabled = true }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaMCPToolDefaultConfig { }; + + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Enabled); + Assert.False(model.RawData.ContainsKey("enabled")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaMCPToolDefaultConfig { }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaMCPToolDefaultConfig + { + // Null should be interpreted as omitted for these properties + DeferLoading = null, + Enabled = null, + }; + + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Enabled); + Assert.False(model.RawData.ContainsKey("enabled")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaMCPToolDefaultConfig + { + // Null should be interpreted as omitted for these properties + DeferLoading = null, + Enabled = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolResultBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolResultBlockTest.cs new file mode 100644 index 00000000..84ea0657 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolResultBlockTest.cs @@ -0,0 +1,82 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMCPToolResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMCPToolResultBlock + { + Content = "string", + IsError = true, + ToolUseID = "tool_use_id", + }; + + BetaMCPToolResultBlockContent expectedContent = "string"; + bool expectedIsError = true; + string expectedToolUseID = "tool_use_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"mcp_tool_result\""); + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedIsError, model.IsError); + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMCPToolResultBlock + { + Content = "string", + IsError = true, + ToolUseID = "tool_use_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMCPToolResultBlock + { + Content = "string", + IsError = true, + ToolUseID = "tool_use_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaMCPToolResultBlockContent expectedContent = "string"; + bool expectedIsError = true; + string expectedToolUseID = "tool_use_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"mcp_tool_result\""); + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedIsError, deserialized.IsError); + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMCPToolResultBlock + { + Content = "string", + IsError = true, + ToolUseID = "tool_use_id", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolUseBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolUseBlockParamTest.cs new file mode 100644 index 00000000..d8c5e2ee --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolUseBlockParamTest.cs @@ -0,0 +1,203 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMCPToolUseBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMCPToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "name", + ServerName = "server_name", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string expectedID = "id"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + string expectedName = "name"; + string expectedServerName = "server_name"; + JsonElement expectedType = JsonSerializer.Deserialize("\"mcp_tool_use\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedInput.Count, model.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(model.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.Input[item.Key])); + } + Assert.Equal(expectedName, model.Name); + Assert.Equal(expectedServerName, model.ServerName); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMCPToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "name", + ServerName = "server_name", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMCPToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "name", + ServerName = "server_name", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "id"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + string expectedName = "name"; + string expectedServerName = "server_name"; + JsonElement expectedType = JsonSerializer.Deserialize("\"mcp_tool_use\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedInput.Count, deserialized.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(deserialized.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.Input[item.Key])); + } + Assert.Equal(expectedName, deserialized.Name); + Assert.Equal(expectedServerName, deserialized.ServerName); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMCPToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "name", + ServerName = "server_name", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaMCPToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "name", + ServerName = "server_name", + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaMCPToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "name", + ServerName = "server_name", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaMCPToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "name", + ServerName = "server_name", + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaMCPToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "name", + ServerName = "server_name", + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolUseBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolUseBlockTest.cs new file mode 100644 index 00000000..97591cec --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolUseBlockTest.cs @@ -0,0 +1,121 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMCPToolUseBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMCPToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "name", + ServerName = "server_name", + }; + + string expectedID = "id"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + string expectedName = "name"; + string expectedServerName = "server_name"; + JsonElement expectedType = JsonSerializer.Deserialize("\"mcp_tool_use\""); + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedInput.Count, model.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(model.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.Input[item.Key])); + } + Assert.Equal(expectedName, model.Name); + Assert.Equal(expectedServerName, model.ServerName); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMCPToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "name", + ServerName = "server_name", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMCPToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "name", + ServerName = "server_name", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "id"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + string expectedName = "name"; + string expectedServerName = "server_name"; + JsonElement expectedType = JsonSerializer.Deserialize("\"mcp_tool_use\""); + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedInput.Count, deserialized.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(deserialized.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.Input[item.Key])); + } + Assert.Equal(expectedName, deserialized.Name); + Assert.Equal(expectedServerName, deserialized.ServerName); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMCPToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "name", + ServerName = "server_name", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolsetTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolsetTest.cs new file mode 100644 index 00000000..44f605b8 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMCPToolsetTest.cs @@ -0,0 +1,291 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMCPToolsetTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMCPToolset + { + MCPServerName = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Configs = new Dictionary() + { + { + "foo", + new() { DeferLoading = true, Enabled = true } + }, + }, + DefaultConfig = new() { DeferLoading = true, Enabled = true }, + }; + + string expectedMCPServerName = "x"; + JsonElement expectedType = JsonSerializer.Deserialize("\"mcp_toolset\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + Dictionary expectedConfigs = new() + { + { + "foo", + new() { DeferLoading = true, Enabled = true } + }, + }; + BetaMCPToolDefaultConfig expectedDefaultConfig = new() + { + DeferLoading = true, + Enabled = true, + }; + + Assert.Equal(expectedMCPServerName, model.MCPServerName); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedConfigs.Count, model.Configs.Count); + foreach (var item in expectedConfigs) + { + Assert.True(model.Configs.TryGetValue(item.Key, out var value)); + + Assert.Equal(value, model.Configs[item.Key]); + } + Assert.Equal(expectedDefaultConfig, model.DefaultConfig); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMCPToolset + { + MCPServerName = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Configs = new Dictionary() + { + { + "foo", + new() { DeferLoading = true, Enabled = true } + }, + }, + DefaultConfig = new() { DeferLoading = true, Enabled = true }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMCPToolset + { + MCPServerName = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Configs = new Dictionary() + { + { + "foo", + new() { DeferLoading = true, Enabled = true } + }, + }, + DefaultConfig = new() { DeferLoading = true, Enabled = true }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMCPServerName = "x"; + JsonElement expectedType = JsonSerializer.Deserialize("\"mcp_toolset\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + Dictionary expectedConfigs = new() + { + { + "foo", + new() { DeferLoading = true, Enabled = true } + }, + }; + BetaMCPToolDefaultConfig expectedDefaultConfig = new() + { + DeferLoading = true, + Enabled = true, + }; + + Assert.Equal(expectedMCPServerName, deserialized.MCPServerName); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedConfigs.Count, deserialized.Configs.Count); + foreach (var item in expectedConfigs) + { + Assert.True(deserialized.Configs.TryGetValue(item.Key, out var value)); + + Assert.Equal(value, deserialized.Configs[item.Key]); + } + Assert.Equal(expectedDefaultConfig, deserialized.DefaultConfig); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMCPToolset + { + MCPServerName = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Configs = new Dictionary() + { + { + "foo", + new() { DeferLoading = true, Enabled = true } + }, + }, + DefaultConfig = new() { DeferLoading = true, Enabled = true }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaMCPToolset + { + MCPServerName = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Configs = new Dictionary() + { + { + "foo", + new() { DeferLoading = true, Enabled = true } + }, + }, + }; + + Assert.Null(model.DefaultConfig); + Assert.False(model.RawData.ContainsKey("default_config")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaMCPToolset + { + MCPServerName = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Configs = new Dictionary() + { + { + "foo", + new() { DeferLoading = true, Enabled = true } + }, + }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaMCPToolset + { + MCPServerName = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Configs = new Dictionary() + { + { + "foo", + new() { DeferLoading = true, Enabled = true } + }, + }, + + // Null should be interpreted as omitted for these properties + DefaultConfig = null, + }; + + Assert.Null(model.DefaultConfig); + Assert.False(model.RawData.ContainsKey("default_config")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaMCPToolset + { + MCPServerName = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Configs = new Dictionary() + { + { + "foo", + new() { DeferLoading = true, Enabled = true } + }, + }, + + // Null should be interpreted as omitted for these properties + DefaultConfig = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaMCPToolset + { + MCPServerName = "x", + DefaultConfig = new() { DeferLoading = true, Enabled = true }, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Configs); + Assert.False(model.RawData.ContainsKey("configs")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaMCPToolset + { + MCPServerName = "x", + DefaultConfig = new() { DeferLoading = true, Enabled = true }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaMCPToolset + { + MCPServerName = "x", + DefaultConfig = new() { DeferLoading = true, Enabled = true }, + + CacheControl = null, + Configs = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Configs); + Assert.True(model.RawData.ContainsKey("configs")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaMCPToolset + { + MCPServerName = "x", + DefaultConfig = new() { DeferLoading = true, Enabled = true }, + + CacheControl = null, + Configs = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818CommandTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818CommandTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818CommandTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818CreateCommandTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818CreateCommandTest.cs new file mode 100644 index 00000000..fea703c1 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818CreateCommandTest.cs @@ -0,0 +1,76 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMemoryTool20250818CreateCommandTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMemoryTool20250818CreateCommand + { + FileText = "Meeting notes:\n- Discussed project timeline\n- Next steps defined\n", + Path = "/memories/notes.txt", + }; + + JsonElement expectedCommand = JsonSerializer.Deserialize("\"create\""); + string expectedFileText = + "Meeting notes:\n- Discussed project timeline\n- Next steps defined\n"; + string expectedPath = "/memories/notes.txt"; + + Assert.True(JsonElement.DeepEquals(expectedCommand, model.Command)); + Assert.Equal(expectedFileText, model.FileText); + Assert.Equal(expectedPath, model.Path); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMemoryTool20250818CreateCommand + { + FileText = "Meeting notes:\n- Discussed project timeline\n- Next steps defined\n", + Path = "/memories/notes.txt", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMemoryTool20250818CreateCommand + { + FileText = "Meeting notes:\n- Discussed project timeline\n- Next steps defined\n", + Path = "/memories/notes.txt", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedCommand = JsonSerializer.Deserialize("\"create\""); + string expectedFileText = + "Meeting notes:\n- Discussed project timeline\n- Next steps defined\n"; + string expectedPath = "/memories/notes.txt"; + + Assert.True(JsonElement.DeepEquals(expectedCommand, deserialized.Command)); + Assert.Equal(expectedFileText, deserialized.FileText); + Assert.Equal(expectedPath, deserialized.Path); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMemoryTool20250818CreateCommand + { + FileText = "Meeting notes:\n- Discussed project timeline\n- Next steps defined\n", + Path = "/memories/notes.txt", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818DeleteCommandTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818DeleteCommandTest.cs new file mode 100644 index 00000000..12995c22 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818DeleteCommandTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMemoryTool20250818DeleteCommandTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMemoryTool20250818DeleteCommand { Path = "/memories/old_file.txt" }; + + JsonElement expectedCommand = JsonSerializer.Deserialize("\"delete\""); + string expectedPath = "/memories/old_file.txt"; + + Assert.True(JsonElement.DeepEquals(expectedCommand, model.Command)); + Assert.Equal(expectedPath, model.Path); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMemoryTool20250818DeleteCommand { Path = "/memories/old_file.txt" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMemoryTool20250818DeleteCommand { Path = "/memories/old_file.txt" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedCommand = JsonSerializer.Deserialize("\"delete\""); + string expectedPath = "/memories/old_file.txt"; + + Assert.True(JsonElement.DeepEquals(expectedCommand, deserialized.Command)); + Assert.Equal(expectedPath, deserialized.Path); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMemoryTool20250818DeleteCommand { Path = "/memories/old_file.txt" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818InsertCommandTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818InsertCommandTest.cs new file mode 100644 index 00000000..444f0e8f --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818InsertCommandTest.cs @@ -0,0 +1,82 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMemoryTool20250818InsertCommandTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMemoryTool20250818InsertCommand + { + InsertLine = 2, + InsertText = "- Review memory tool documentation\n", + Path = "/memories/todo.txt", + }; + + JsonElement expectedCommand = JsonSerializer.Deserialize("\"insert\""); + long expectedInsertLine = 2; + string expectedInsertText = "- Review memory tool documentation\n"; + string expectedPath = "/memories/todo.txt"; + + Assert.True(JsonElement.DeepEquals(expectedCommand, model.Command)); + Assert.Equal(expectedInsertLine, model.InsertLine); + Assert.Equal(expectedInsertText, model.InsertText); + Assert.Equal(expectedPath, model.Path); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMemoryTool20250818InsertCommand + { + InsertLine = 2, + InsertText = "- Review memory tool documentation\n", + Path = "/memories/todo.txt", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMemoryTool20250818InsertCommand + { + InsertLine = 2, + InsertText = "- Review memory tool documentation\n", + Path = "/memories/todo.txt", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedCommand = JsonSerializer.Deserialize("\"insert\""); + long expectedInsertLine = 2; + string expectedInsertText = "- Review memory tool documentation\n"; + string expectedPath = "/memories/todo.txt"; + + Assert.True(JsonElement.DeepEquals(expectedCommand, deserialized.Command)); + Assert.Equal(expectedInsertLine, deserialized.InsertLine); + Assert.Equal(expectedInsertText, deserialized.InsertText); + Assert.Equal(expectedPath, deserialized.Path); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMemoryTool20250818InsertCommand + { + InsertLine = 2, + InsertText = "- Review memory tool documentation\n", + Path = "/memories/todo.txt", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818RenameCommandTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818RenameCommandTest.cs new file mode 100644 index 00000000..7746fa21 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818RenameCommandTest.cs @@ -0,0 +1,74 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMemoryTool20250818RenameCommandTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMemoryTool20250818RenameCommand + { + NewPath = "/memories/final.txt", + OldPath = "/memories/draft.txt", + }; + + JsonElement expectedCommand = JsonSerializer.Deserialize("\"rename\""); + string expectedNewPath = "/memories/final.txt"; + string expectedOldPath = "/memories/draft.txt"; + + Assert.True(JsonElement.DeepEquals(expectedCommand, model.Command)); + Assert.Equal(expectedNewPath, model.NewPath); + Assert.Equal(expectedOldPath, model.OldPath); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMemoryTool20250818RenameCommand + { + NewPath = "/memories/final.txt", + OldPath = "/memories/draft.txt", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMemoryTool20250818RenameCommand + { + NewPath = "/memories/final.txt", + OldPath = "/memories/draft.txt", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedCommand = JsonSerializer.Deserialize("\"rename\""); + string expectedNewPath = "/memories/final.txt"; + string expectedOldPath = "/memories/draft.txt"; + + Assert.True(JsonElement.DeepEquals(expectedCommand, deserialized.Command)); + Assert.Equal(expectedNewPath, deserialized.NewPath); + Assert.Equal(expectedOldPath, deserialized.OldPath); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMemoryTool20250818RenameCommand + { + NewPath = "/memories/final.txt", + OldPath = "/memories/draft.txt", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818StrReplaceCommandTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818StrReplaceCommandTest.cs new file mode 100644 index 00000000..30ca67db --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818StrReplaceCommandTest.cs @@ -0,0 +1,86 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMemoryTool20250818StrReplaceCommandTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMemoryTool20250818StrReplaceCommand + { + NewStr = "Favorite color: green", + OldStr = "Favorite color: blue", + Path = "/memories/preferences.txt", + }; + + JsonElement expectedCommand = JsonSerializer.Deserialize("\"str_replace\""); + string expectedNewStr = "Favorite color: green"; + string expectedOldStr = "Favorite color: blue"; + string expectedPath = "/memories/preferences.txt"; + + Assert.True(JsonElement.DeepEquals(expectedCommand, model.Command)); + Assert.Equal(expectedNewStr, model.NewStr); + Assert.Equal(expectedOldStr, model.OldStr); + Assert.Equal(expectedPath, model.Path); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMemoryTool20250818StrReplaceCommand + { + NewStr = "Favorite color: green", + OldStr = "Favorite color: blue", + Path = "/memories/preferences.txt", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMemoryTool20250818StrReplaceCommand + { + NewStr = "Favorite color: green", + OldStr = "Favorite color: blue", + Path = "/memories/preferences.txt", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + Assert.NotNull(deserialized); + + JsonElement expectedCommand = JsonSerializer.Deserialize("\"str_replace\""); + string expectedNewStr = "Favorite color: green"; + string expectedOldStr = "Favorite color: blue"; + string expectedPath = "/memories/preferences.txt"; + + Assert.True(JsonElement.DeepEquals(expectedCommand, deserialized.Command)); + Assert.Equal(expectedNewStr, deserialized.NewStr); + Assert.Equal(expectedOldStr, deserialized.OldStr); + Assert.Equal(expectedPath, deserialized.Path); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMemoryTool20250818StrReplaceCommand + { + NewStr = "Favorite color: green", + OldStr = "Favorite color: blue", + Path = "/memories/preferences.txt", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818Test.cs new file mode 100644 index 00000000..e4aba28e --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818Test.cs @@ -0,0 +1,383 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMemoryTool20250818Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMemoryTool20250818 + { + AllowedCallers = [BetaMemoryTool20250818AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + JsonElement expectedName = JsonSerializer.Deserialize("\"memory\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"memory_20250818\""); + List> expectedAllowedCallers = + [ + BetaMemoryTool20250818AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedInputExamples.Count, model.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, model.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(model.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, model.Strict); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMemoryTool20250818 + { + AllowedCallers = [BetaMemoryTool20250818AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMemoryTool20250818 + { + AllowedCallers = [BetaMemoryTool20250818AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize("\"memory\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"memory_20250818\""); + List> expectedAllowedCallers = + [ + BetaMemoryTool20250818AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedInputExamples.Count, deserialized.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, deserialized.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(deserialized.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, deserialized.Strict); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMemoryTool20250818 + { + AllowedCallers = [BetaMemoryTool20250818AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaMemoryTool20250818 { CacheControl = new() { TTL = TTL.TTL5m } }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaMemoryTool20250818 { CacheControl = new() { TTL = TTL.TTL5m } }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaMemoryTool20250818 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaMemoryTool20250818 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaMemoryTool20250818 + { + AllowedCallers = [BetaMemoryTool20250818AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaMemoryTool20250818 + { + AllowedCallers = [BetaMemoryTool20250818AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaMemoryTool20250818 + { + AllowedCallers = [BetaMemoryTool20250818AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaMemoryTool20250818 + { + AllowedCallers = [BetaMemoryTool20250818AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + }; + + model.Validate(); + } +} + +public class BetaMemoryTool20250818AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaMemoryTool20250818AllowedCaller.Direct)] + [InlineData(BetaMemoryTool20250818AllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaMemoryTool20250818AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaMemoryTool20250818AllowedCaller.Direct)] + [InlineData(BetaMemoryTool20250818AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaMemoryTool20250818AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818ViewCommandTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818ViewCommandTest.cs new file mode 100644 index 00000000..e5441ffa --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMemoryTool20250818ViewCommandTest.cs @@ -0,0 +1,129 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMemoryTool20250818ViewCommandTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMemoryTool20250818ViewCommand + { + Path = "/memories", + ViewRange = [1, 10], + }; + + JsonElement expectedCommand = JsonSerializer.Deserialize("\"view\""); + string expectedPath = "/memories"; + List expectedViewRange = [1, 10]; + + Assert.True(JsonElement.DeepEquals(expectedCommand, model.Command)); + Assert.Equal(expectedPath, model.Path); + Assert.Equal(expectedViewRange.Count, model.ViewRange.Count); + for (int i = 0; i < expectedViewRange.Count; i++) + { + Assert.Equal(expectedViewRange[i], model.ViewRange[i]); + } + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMemoryTool20250818ViewCommand + { + Path = "/memories", + ViewRange = [1, 10], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMemoryTool20250818ViewCommand + { + Path = "/memories", + ViewRange = [1, 10], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedCommand = JsonSerializer.Deserialize("\"view\""); + string expectedPath = "/memories"; + List expectedViewRange = [1, 10]; + + Assert.True(JsonElement.DeepEquals(expectedCommand, deserialized.Command)); + Assert.Equal(expectedPath, deserialized.Path); + Assert.Equal(expectedViewRange.Count, deserialized.ViewRange.Count); + for (int i = 0; i < expectedViewRange.Count; i++) + { + Assert.Equal(expectedViewRange[i], deserialized.ViewRange[i]); + } + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMemoryTool20250818ViewCommand + { + Path = "/memories", + ViewRange = [1, 10], + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaMemoryTool20250818ViewCommand { Path = "/memories" }; + + Assert.Null(model.ViewRange); + Assert.False(model.RawData.ContainsKey("view_range")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaMemoryTool20250818ViewCommand { Path = "/memories" }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaMemoryTool20250818ViewCommand + { + Path = "/memories", + + // Null should be interpreted as omitted for these properties + ViewRange = null, + }; + + Assert.Null(model.ViewRange); + Assert.False(model.RawData.ContainsKey("view_range")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaMemoryTool20250818ViewCommand + { + Path = "/memories", + + // Null should be interpreted as omitted for these properties + ViewRange = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMessageDeltaUsageTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMessageDeltaUsageTest.cs new file mode 100644 index 00000000..6d610abc --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMessageDeltaUsageTest.cs @@ -0,0 +1,102 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMessageDeltaUsageTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMessageDeltaUsage + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + }; + + long expectedCacheCreationInputTokens = 2051; + long expectedCacheReadInputTokens = 2051; + long expectedInputTokens = 2095; + long expectedOutputTokens = 503; + BetaServerToolUsage expectedServerToolUse = new() + { + WebFetchRequests = 2, + WebSearchRequests = 0, + }; + + Assert.Equal(expectedCacheCreationInputTokens, model.CacheCreationInputTokens); + Assert.Equal(expectedCacheReadInputTokens, model.CacheReadInputTokens); + Assert.Equal(expectedInputTokens, model.InputTokens); + Assert.Equal(expectedOutputTokens, model.OutputTokens); + Assert.Equal(expectedServerToolUse, model.ServerToolUse); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMessageDeltaUsage + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMessageDeltaUsage + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedCacheCreationInputTokens = 2051; + long expectedCacheReadInputTokens = 2051; + long expectedInputTokens = 2095; + long expectedOutputTokens = 503; + BetaServerToolUsage expectedServerToolUse = new() + { + WebFetchRequests = 2, + WebSearchRequests = 0, + }; + + Assert.Equal(expectedCacheCreationInputTokens, deserialized.CacheCreationInputTokens); + Assert.Equal(expectedCacheReadInputTokens, deserialized.CacheReadInputTokens); + Assert.Equal(expectedInputTokens, deserialized.InputTokens); + Assert.Equal(expectedOutputTokens, deserialized.OutputTokens); + Assert.Equal(expectedServerToolUse, deserialized.ServerToolUse); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMessageDeltaUsage + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMessageParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMessageParamTest.cs new file mode 100644 index 00000000..936ac2f9 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMessageParamTest.cs @@ -0,0 +1,112 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMessageParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMessageParam { Content = "string", Role = Role.User }; + + BetaMessageParamContent expectedContent = "string"; + ApiEnum expectedRole = Role.User; + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedRole, model.Role); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMessageParam { Content = "string", Role = Role.User }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMessageParam { Content = "string", Role = Role.User }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaMessageParamContent expectedContent = "string"; + ApiEnum expectedRole = Role.User; + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedRole, deserialized.Role); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMessageParam { Content = "string", Role = Role.User }; + + model.Validate(); + } +} + +public class RoleTest : TestBase +{ + [Theory] + [InlineData(Role.User)] + [InlineData(Role.Assistant)] + public void Validation_Works(Role rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(Role.User)] + [InlineData(Role.Assistant)] + public void SerializationRoundtrip_Works(Role rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMessageTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMessageTest.cs new file mode 100644 index 00000000..b8b611fc --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMessageTest.cs @@ -0,0 +1,428 @@ +using System; +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Models.Messages; +using Messages = Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMessageTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Messages::BetaMessage + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }; + + string expectedID = "msg_013Zva2CMHLNnXjNJJKqJ2EF"; + Messages::BetaContainer expectedContainer = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }; + List expectedContent = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ]; + Messages::BetaContextManagementResponse expectedContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ); + ApiEnum expectedModel = Model.ClaudeOpus4_5_20251101; + JsonElement expectedRole = JsonSerializer.Deserialize("\"assistant\""); + ApiEnum expectedStopReason = + Messages::BetaStopReason.EndTurn; + string expectedStopSequence = null; + JsonElement expectedType = JsonSerializer.Deserialize("\"message\""); + Messages::BetaUsage expectedUsage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedContainer, model.Container); + Assert.Equal(expectedContent.Count, model.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], model.Content[i]); + } + Assert.Equal(expectedContextManagement, model.ContextManagement); + Assert.Equal(expectedModel, model.Model); + Assert.True(JsonElement.DeepEquals(expectedRole, model.Role)); + Assert.Equal(expectedStopReason, model.StopReason); + Assert.Equal(expectedStopSequence, model.StopSequence); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedUsage, model.Usage); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Messages::BetaMessage + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Messages::BetaMessage + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "msg_013Zva2CMHLNnXjNJJKqJ2EF"; + Messages::BetaContainer expectedContainer = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }; + List expectedContent = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ]; + Messages::BetaContextManagementResponse expectedContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ); + ApiEnum expectedModel = Model.ClaudeOpus4_5_20251101; + JsonElement expectedRole = JsonSerializer.Deserialize("\"assistant\""); + ApiEnum expectedStopReason = + Messages::BetaStopReason.EndTurn; + string expectedStopSequence = null; + JsonElement expectedType = JsonSerializer.Deserialize("\"message\""); + Messages::BetaUsage expectedUsage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedContainer, deserialized.Container); + Assert.Equal(expectedContent.Count, deserialized.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], deserialized.Content[i]); + } + Assert.Equal(expectedContextManagement, deserialized.ContextManagement); + Assert.Equal(expectedModel, deserialized.Model); + Assert.True(JsonElement.DeepEquals(expectedRole, deserialized.Role)); + Assert.Equal(expectedStopReason, deserialized.StopReason); + Assert.Equal(expectedStopSequence, deserialized.StopSequence); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedUsage, deserialized.Usage); + } + + [Fact] + public void Validation_Works() + { + var model = new Messages::BetaMessage + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMessageTokensCountTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMessageTokensCountTest.cs new file mode 100644 index 00000000..78630675 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMessageTokensCountTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMessageTokensCountTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMessageTokensCount { ContextManagement = new(0), InputTokens = 2095 }; + + BetaCountTokensContextManagementResponse expectedContextManagement = new(0); + long expectedInputTokens = 2095; + + Assert.Equal(expectedContextManagement, model.ContextManagement); + Assert.Equal(expectedInputTokens, model.InputTokens); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMessageTokensCount { ContextManagement = new(0), InputTokens = 2095 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMessageTokensCount { ContextManagement = new(0), InputTokens = 2095 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaCountTokensContextManagementResponse expectedContextManagement = new(0); + long expectedInputTokens = 2095; + + Assert.Equal(expectedContextManagement, deserialized.ContextManagement); + Assert.Equal(expectedInputTokens, deserialized.InputTokens); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMessageTokensCount { ContextManagement = new(0), InputTokens = 2095 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaMetadataTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaMetadataTest.cs new file mode 100644 index 00000000..c7b55ad9 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaMetadataTest.cs @@ -0,0 +1,84 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaMetadataTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaMetadata { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }; + + string expectedUserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b"; + + Assert.Equal(expectedUserID, model.UserID); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaMetadata { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaMetadata { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedUserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b"; + + Assert.Equal(expectedUserID, deserialized.UserID); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaMetadata { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaMetadata { }; + + Assert.Null(model.UserID); + Assert.False(model.RawData.ContainsKey("user_id")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaMetadata { }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaMetadata { UserID = null }; + + Assert.Null(model.UserID); + Assert.True(model.RawData.ContainsKey("user_id")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaMetadata { UserID = null }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaOutputConfigTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaOutputConfigTest.cs new file mode 100644 index 00000000..ac62f258 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaOutputConfigTest.cs @@ -0,0 +1,144 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaOutputConfigTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaOutputConfig { Effort = Effort.Low }; + + ApiEnum expectedEffort = Effort.Low; + + Assert.Equal(expectedEffort, model.Effort); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaOutputConfig { Effort = Effort.Low }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaOutputConfig { Effort = Effort.Low }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ApiEnum expectedEffort = Effort.Low; + + Assert.Equal(expectedEffort, deserialized.Effort); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaOutputConfig { Effort = Effort.Low }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaOutputConfig { }; + + Assert.Null(model.Effort); + Assert.False(model.RawData.ContainsKey("effort")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaOutputConfig { }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaOutputConfig { Effort = null }; + + Assert.Null(model.Effort); + Assert.True(model.RawData.ContainsKey("effort")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaOutputConfig { Effort = null }; + + model.Validate(); + } +} + +public class EffortTest : TestBase +{ + [Theory] + [InlineData(Effort.Low)] + [InlineData(Effort.Medium)] + [InlineData(Effort.High)] + public void Validation_Works(Effort rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(Effort.Low)] + [InlineData(Effort.Medium)] + [InlineData(Effort.High)] + public void SerializationRoundtrip_Works(Effort rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaPlainTextSourceTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaPlainTextSourceTest.cs new file mode 100644 index 00000000..20a6a5bf --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaPlainTextSourceTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaPlainTextSourceTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaPlainTextSource { Data = "data" }; + + string expectedData = "data"; + JsonElement expectedMediaType = JsonSerializer.Deserialize("\"text/plain\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"text\""); + + Assert.Equal(expectedData, model.Data); + Assert.True(JsonElement.DeepEquals(expectedMediaType, model.MediaType)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaPlainTextSource { Data = "data" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaPlainTextSource { Data = "data" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedData = "data"; + JsonElement expectedMediaType = JsonSerializer.Deserialize("\"text/plain\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"text\""); + + Assert.Equal(expectedData, deserialized.Data); + Assert.True(JsonElement.DeepEquals(expectedMediaType, deserialized.MediaType)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaPlainTextSource { Data = "data" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaRawContentBlockDeltaEventTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawContentBlockDeltaEventTest.cs new file mode 100644 index 00000000..d4cfc5e9 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawContentBlockDeltaEventTest.cs @@ -0,0 +1,78 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaRawContentBlockDeltaEventTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaRawContentBlockDeltaEvent + { + Delta = new BetaTextDelta("text"), + Index = 0, + }; + + BetaRawContentBlockDelta expectedDelta = new BetaTextDelta("text"); + long expectedIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_delta\"" + ); + + Assert.Equal(expectedDelta, model.Delta); + Assert.Equal(expectedIndex, model.Index); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaRawContentBlockDeltaEvent + { + Delta = new BetaTextDelta("text"), + Index = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaRawContentBlockDeltaEvent + { + Delta = new BetaTextDelta("text"), + Index = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaRawContentBlockDelta expectedDelta = new BetaTextDelta("text"); + long expectedIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_delta\"" + ); + + Assert.Equal(expectedDelta, deserialized.Delta); + Assert.Equal(expectedIndex, deserialized.Index); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaRawContentBlockDeltaEvent + { + Delta = new BetaTextDelta("text"), + Index = 0, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaRawContentBlockDeltaTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawContentBlockDeltaTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawContentBlockDeltaTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaRawContentBlockStartEventTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawContentBlockStartEventTest.cs new file mode 100644 index 00000000..a697f011 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawContentBlockStartEventTest.cs @@ -0,0 +1,168 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaRawContentBlockStartEventTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaRawContentBlockStartEvent + { + ContentBlock = new BetaTextBlock() + { + Citations = + [ + new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }, + Index = 0, + }; + + ContentBlock expectedContentBlock = new BetaTextBlock() + { + Citations = + [ + new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }; + long expectedIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_start\"" + ); + + Assert.Equal(expectedContentBlock, model.ContentBlock); + Assert.Equal(expectedIndex, model.Index); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaRawContentBlockStartEvent + { + ContentBlock = new BetaTextBlock() + { + Citations = + [ + new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }, + Index = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaRawContentBlockStartEvent + { + ContentBlock = new BetaTextBlock() + { + Citations = + [ + new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }, + Index = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ContentBlock expectedContentBlock = new BetaTextBlock() + { + Citations = + [ + new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }; + long expectedIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_start\"" + ); + + Assert.Equal(expectedContentBlock, deserialized.ContentBlock); + Assert.Equal(expectedIndex, deserialized.Index); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaRawContentBlockStartEvent + { + ContentBlock = new BetaTextBlock() + { + Citations = + [ + new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }, + Index = 0, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaRawContentBlockStopEventTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawContentBlockStopEventTest.cs new file mode 100644 index 00000000..5182f095 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawContentBlockStopEventTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaRawContentBlockStopEventTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaRawContentBlockStopEvent { Index = 0 }; + + long expectedIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_stop\"" + ); + + Assert.Equal(expectedIndex, model.Index); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaRawContentBlockStopEvent { Index = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaRawContentBlockStopEvent { Index = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_stop\"" + ); + + Assert.Equal(expectedIndex, deserialized.Index); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaRawContentBlockStopEvent { Index = 0 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaRawMessageDeltaEventTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawMessageDeltaEventTest.cs new file mode 100644 index 00000000..e46c6893 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawMessageDeltaEventTest.cs @@ -0,0 +1,436 @@ +using System; +using System.Text.Json; +using Anthropic.Core; +using Messages = Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaRawMessageDeltaEventTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Messages::BetaRawMessageDeltaEvent + { + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Delta = new() + { + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = "stop_sequence", + }, + Usage = new() + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + }, + }; + + Messages::BetaContextManagementResponse expectedContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ); + Messages::Delta expectedDelta = new() + { + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = "stop_sequence", + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"message_delta\""); + Messages::BetaMessageDeltaUsage expectedUsage = new() + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + }; + + Assert.Equal(expectedContextManagement, model.ContextManagement); + Assert.Equal(expectedDelta, model.Delta); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedUsage, model.Usage); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Messages::BetaRawMessageDeltaEvent + { + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Delta = new() + { + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = "stop_sequence", + }, + Usage = new() + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Messages::BetaRawMessageDeltaEvent + { + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Delta = new() + { + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = "stop_sequence", + }, + Usage = new() + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + Messages::BetaContextManagementResponse expectedContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ); + Messages::Delta expectedDelta = new() + { + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = "stop_sequence", + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"message_delta\""); + Messages::BetaMessageDeltaUsage expectedUsage = new() + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + }; + + Assert.Equal(expectedContextManagement, deserialized.ContextManagement); + Assert.Equal(expectedDelta, deserialized.Delta); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedUsage, deserialized.Usage); + } + + [Fact] + public void Validation_Works() + { + var model = new Messages::BetaRawMessageDeltaEvent + { + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Delta = new() + { + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = "stop_sequence", + }, + Usage = new() + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + }, + }; + + model.Validate(); + } +} + +public class DeltaTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Messages::Delta + { + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = "stop_sequence", + }; + + Messages::BetaContainer expectedContainer = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }; + ApiEnum expectedStopReason = + Messages::BetaStopReason.EndTurn; + string expectedStopSequence = "stop_sequence"; + + Assert.Equal(expectedContainer, model.Container); + Assert.Equal(expectedStopReason, model.StopReason); + Assert.Equal(expectedStopSequence, model.StopSequence); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Messages::Delta + { + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = "stop_sequence", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Messages::Delta + { + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = "stop_sequence", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + Messages::BetaContainer expectedContainer = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }; + ApiEnum expectedStopReason = + Messages::BetaStopReason.EndTurn; + string expectedStopSequence = "stop_sequence"; + + Assert.Equal(expectedContainer, deserialized.Container); + Assert.Equal(expectedStopReason, deserialized.StopReason); + Assert.Equal(expectedStopSequence, deserialized.StopSequence); + } + + [Fact] + public void Validation_Works() + { + var model = new Messages::Delta + { + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = "stop_sequence", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaRawMessageStartEventTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawMessageStartEventTest.cs new file mode 100644 index 00000000..806dd017 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawMessageStartEventTest.cs @@ -0,0 +1,432 @@ +using System; +using System.Text.Json; +using Anthropic.Models.Messages; +using Messages = Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaRawMessageStartEventTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Messages::BetaRawMessageStartEvent + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }, + }; + + Messages::BetaMessage expectedMessage = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"message_start\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Messages::BetaRawMessageStartEvent + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Messages::BetaRawMessageStartEvent + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + Messages::BetaMessage expectedMessage = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"message_start\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new Messages::BetaRawMessageStartEvent + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Container = new() + { + ID = "id", + ExpiresAt = DateTimeOffset.Parse("2019-12-27T18:11:19.117Z"), + Skills = + [ + new() + { + SkillID = "x", + Type = Messages::Type.Anthropic, + Version = "x", + }, + ], + }, + Content = + [ + new Messages::BetaTextBlock() + { + Citations = + [ + new Messages::BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + ContextManagement = new( + [ + new Messages::BetaClearToolUses20250919EditResponse() + { + ClearedInputTokens = 0, + ClearedToolUses = 0, + }, + ] + ), + Model = Model.ClaudeOpus4_5_20251101, + StopReason = Messages::BetaStopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = Messages::BetaUsageServiceTier.Standard, + }, + }, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaRawMessageStopEventTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawMessageStopEventTest.cs new file mode 100644 index 00000000..9aa29b2f --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawMessageStopEventTest.cs @@ -0,0 +1,50 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaRawMessageStopEventTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaRawMessageStopEvent { }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"message_stop\""); + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaRawMessageStopEvent { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaRawMessageStopEvent { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"message_stop\""); + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaRawMessageStopEvent { }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaRawMessageStreamEventTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawMessageStreamEventTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaRawMessageStreamEventTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaRedactedThinkingBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaRedactedThinkingBlockParamTest.cs new file mode 100644 index 00000000..0b2960c7 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaRedactedThinkingBlockParamTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaRedactedThinkingBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaRedactedThinkingBlockParam { Data = "data" }; + + string expectedData = "data"; + JsonElement expectedType = JsonSerializer.Deserialize("\"redacted_thinking\""); + + Assert.Equal(expectedData, model.Data); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaRedactedThinkingBlockParam { Data = "data" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaRedactedThinkingBlockParam { Data = "data" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedData = "data"; + JsonElement expectedType = JsonSerializer.Deserialize("\"redacted_thinking\""); + + Assert.Equal(expectedData, deserialized.Data); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaRedactedThinkingBlockParam { Data = "data" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaRedactedThinkingBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaRedactedThinkingBlockTest.cs new file mode 100644 index 00000000..ca208354 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaRedactedThinkingBlockTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaRedactedThinkingBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaRedactedThinkingBlock { Data = "data" }; + + string expectedData = "data"; + JsonElement expectedType = JsonSerializer.Deserialize("\"redacted_thinking\""); + + Assert.Equal(expectedData, model.Data); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaRedactedThinkingBlock { Data = "data" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaRedactedThinkingBlock { Data = "data" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedData = "data"; + JsonElement expectedType = JsonSerializer.Deserialize("\"redacted_thinking\""); + + Assert.Equal(expectedData, deserialized.Data); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaRedactedThinkingBlock { Data = "data" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaRequestDocumentBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaRequestDocumentBlockTest.cs new file mode 100644 index 00000000..1b7a45c1 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaRequestDocumentBlockTest.cs @@ -0,0 +1,170 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaRequestDocumentBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaRequestDocumentBlock + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }; + + BetaRequestDocumentBlockSource expectedSource = new BetaBase64PDFSource( + "U3RhaW5sZXNzIHJvY2tz" + ); + JsonElement expectedType = JsonSerializer.Deserialize("\"document\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + BetaCitationsConfigParam expectedCitations = new() { Enabled = true }; + string expectedContext = "x"; + string expectedTitle = "x"; + + Assert.Equal(expectedSource, model.Source); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedCitations, model.Citations); + Assert.Equal(expectedContext, model.Context); + Assert.Equal(expectedTitle, model.Title); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaRequestDocumentBlock + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaRequestDocumentBlock + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaRequestDocumentBlockSource expectedSource = new BetaBase64PDFSource( + "U3RhaW5sZXNzIHJvY2tz" + ); + JsonElement expectedType = JsonSerializer.Deserialize("\"document\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + BetaCitationsConfigParam expectedCitations = new() { Enabled = true }; + string expectedContext = "x"; + string expectedTitle = "x"; + + Assert.Equal(expectedSource, deserialized.Source); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedCitations, deserialized.Citations); + Assert.Equal(expectedContext, deserialized.Context); + Assert.Equal(expectedTitle, deserialized.Title); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaRequestDocumentBlock + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaRequestDocumentBlock + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Citations); + Assert.False(model.RawData.ContainsKey("citations")); + Assert.Null(model.Context); + Assert.False(model.RawData.ContainsKey("context")); + Assert.Null(model.Title); + Assert.False(model.RawData.ContainsKey("title")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaRequestDocumentBlock + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaRequestDocumentBlock + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + + CacheControl = null, + Citations = null, + Context = null, + Title = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Citations); + Assert.True(model.RawData.ContainsKey("citations")); + Assert.Null(model.Context); + Assert.True(model.RawData.ContainsKey("context")); + Assert.Null(model.Title); + Assert.True(model.RawData.ContainsKey("title")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaRequestDocumentBlock + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + + CacheControl = null, + Citations = null, + Context = null, + Title = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaRequestMCPServerToolConfigurationTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaRequestMCPServerToolConfigurationTest.cs new file mode 100644 index 00000000..17ec349c --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaRequestMCPServerToolConfigurationTest.cs @@ -0,0 +1,125 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaRequestMCPServerToolConfigurationTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaRequestMCPServerToolConfiguration + { + AllowedTools = ["string"], + Enabled = true, + }; + + List expectedAllowedTools = ["string"]; + bool expectedEnabled = true; + + Assert.Equal(expectedAllowedTools.Count, model.AllowedTools.Count); + for (int i = 0; i < expectedAllowedTools.Count; i++) + { + Assert.Equal(expectedAllowedTools[i], model.AllowedTools[i]); + } + Assert.Equal(expectedEnabled, model.Enabled); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaRequestMCPServerToolConfiguration + { + AllowedTools = ["string"], + Enabled = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaRequestMCPServerToolConfiguration + { + AllowedTools = ["string"], + Enabled = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedAllowedTools = ["string"]; + bool expectedEnabled = true; + + Assert.Equal(expectedAllowedTools.Count, deserialized.AllowedTools.Count); + for (int i = 0; i < expectedAllowedTools.Count; i++) + { + Assert.Equal(expectedAllowedTools[i], deserialized.AllowedTools[i]); + } + Assert.Equal(expectedEnabled, deserialized.Enabled); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaRequestMCPServerToolConfiguration + { + AllowedTools = ["string"], + Enabled = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaRequestMCPServerToolConfiguration { }; + + Assert.Null(model.AllowedTools); + Assert.False(model.RawData.ContainsKey("allowed_tools")); + Assert.Null(model.Enabled); + Assert.False(model.RawData.ContainsKey("enabled")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaRequestMCPServerToolConfiguration { }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaRequestMCPServerToolConfiguration + { + AllowedTools = null, + Enabled = null, + }; + + Assert.Null(model.AllowedTools); + Assert.True(model.RawData.ContainsKey("allowed_tools")); + Assert.Null(model.Enabled); + Assert.True(model.RawData.ContainsKey("enabled")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaRequestMCPServerToolConfiguration + { + AllowedTools = null, + Enabled = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaRequestMCPServerURLDefinitionTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaRequestMCPServerURLDefinitionTest.cs new file mode 100644 index 00000000..0cc819c3 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaRequestMCPServerURLDefinitionTest.cs @@ -0,0 +1,150 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaRequestMCPServerURLDefinitionTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaRequestMCPServerURLDefinition + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }; + + string expectedName = "name"; + JsonElement expectedType = JsonSerializer.Deserialize("\"url\""); + string expectedURL = "url"; + string expectedAuthorizationToken = "authorization_token"; + BetaRequestMCPServerToolConfiguration expectedToolConfiguration = new() + { + AllowedTools = ["string"], + Enabled = true, + }; + + Assert.Equal(expectedName, model.Name); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedURL, model.URL); + Assert.Equal(expectedAuthorizationToken, model.AuthorizationToken); + Assert.Equal(expectedToolConfiguration, model.ToolConfiguration); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaRequestMCPServerURLDefinition + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaRequestMCPServerURLDefinition + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedName = "name"; + JsonElement expectedType = JsonSerializer.Deserialize("\"url\""); + string expectedURL = "url"; + string expectedAuthorizationToken = "authorization_token"; + BetaRequestMCPServerToolConfiguration expectedToolConfiguration = new() + { + AllowedTools = ["string"], + Enabled = true, + }; + + Assert.Equal(expectedName, deserialized.Name); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedURL, deserialized.URL); + Assert.Equal(expectedAuthorizationToken, deserialized.AuthorizationToken); + Assert.Equal(expectedToolConfiguration, deserialized.ToolConfiguration); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaRequestMCPServerURLDefinition + { + Name = "name", + URL = "url", + AuthorizationToken = "authorization_token", + ToolConfiguration = new() { AllowedTools = ["string"], Enabled = true }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaRequestMCPServerURLDefinition { Name = "name", URL = "url" }; + + Assert.Null(model.AuthorizationToken); + Assert.False(model.RawData.ContainsKey("authorization_token")); + Assert.Null(model.ToolConfiguration); + Assert.False(model.RawData.ContainsKey("tool_configuration")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaRequestMCPServerURLDefinition { Name = "name", URL = "url" }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaRequestMCPServerURLDefinition + { + Name = "name", + URL = "url", + + AuthorizationToken = null, + ToolConfiguration = null, + }; + + Assert.Null(model.AuthorizationToken); + Assert.True(model.RawData.ContainsKey("authorization_token")); + Assert.Null(model.ToolConfiguration); + Assert.True(model.RawData.ContainsKey("tool_configuration")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaRequestMCPServerURLDefinition + { + Name = "name", + URL = "url", + + AuthorizationToken = null, + ToolConfiguration = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaRequestMCPToolResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaRequestMCPToolResultBlockParamTest.cs new file mode 100644 index 00000000..4ccde7fb --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaRequestMCPToolResultBlockParamTest.cs @@ -0,0 +1,210 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaRequestMCPToolResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaRequestMCPToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + Content = "string", + IsError = true, + }; + + string expectedToolUseID = "tool_use_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"mcp_tool_result\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + BetaRequestMCPToolResultBlockParamContent expectedContent = "string"; + bool expectedIsError = true; + + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedIsError, model.IsError); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaRequestMCPToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + Content = "string", + IsError = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaRequestMCPToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + Content = "string", + IsError = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedToolUseID = "tool_use_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"mcp_tool_result\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + BetaRequestMCPToolResultBlockParamContent expectedContent = "string"; + bool expectedIsError = true; + + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedIsError, deserialized.IsError); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaRequestMCPToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + Content = "string", + IsError = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaRequestMCPToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + Assert.Null(model.Content); + Assert.False(model.RawData.ContainsKey("content")); + Assert.Null(model.IsError); + Assert.False(model.RawData.ContainsKey("is_error")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaRequestMCPToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaRequestMCPToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + Content = null, + IsError = null, + }; + + Assert.Null(model.Content); + Assert.False(model.RawData.ContainsKey("content")); + Assert.Null(model.IsError); + Assert.False(model.RawData.ContainsKey("is_error")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaRequestMCPToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + Content = null, + IsError = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaRequestMCPToolResultBlockParam + { + ToolUseID = "tool_use_id", + Content = "string", + IsError = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaRequestMCPToolResultBlockParam + { + ToolUseID = "tool_use_id", + Content = "string", + IsError = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaRequestMCPToolResultBlockParam + { + ToolUseID = "tool_use_id", + Content = "string", + IsError = true, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaRequestMCPToolResultBlockParam + { + ToolUseID = "tool_use_id", + Content = "string", + IsError = true, + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaSearchResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaSearchResultBlockParamTest.cs new file mode 100644 index 00000000..32904db1 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaSearchResultBlockParamTest.cs @@ -0,0 +1,485 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaSearchResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaSearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + }; + + List expectedContent = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ]; + string expectedSource = "source"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize("\"search_result\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + BetaCitationsConfigParam expectedCitations = new() { Enabled = true }; + + Assert.Equal(expectedContent.Count, model.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], model.Content[i]); + } + Assert.Equal(expectedSource, model.Source); + Assert.Equal(expectedTitle, model.Title); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedCitations, model.Citations); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaSearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaSearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedContent = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ]; + string expectedSource = "source"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize("\"search_result\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + BetaCitationsConfigParam expectedCitations = new() { Enabled = true }; + + Assert.Equal(expectedContent.Count, deserialized.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], deserialized.Content[i]); + } + Assert.Equal(expectedSource, deserialized.Source); + Assert.Equal(expectedTitle, deserialized.Title); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedCitations, deserialized.Citations); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaSearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaSearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + Assert.Null(model.Citations); + Assert.False(model.RawData.ContainsKey("citations")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaSearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaSearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + Citations = null, + }; + + Assert.Null(model.Citations); + Assert.False(model.RawData.ContainsKey("citations")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaSearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + Citations = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaSearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + Citations = new() { Enabled = true }, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaSearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + Citations = new() { Enabled = true }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaSearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + Citations = new() { Enabled = true }, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaSearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + Citations = new() { Enabled = true }, + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaServerToolCallerTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaServerToolCallerTest.cs new file mode 100644 index 00000000..6c1532fd --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaServerToolCallerTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaServerToolCallerTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaServerToolCaller { ToolID = "srvtoolu_SQfNkl1n_JR_" }; + + string expectedToolID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_20250825\"" + ); + + Assert.Equal(expectedToolID, model.ToolID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaServerToolCaller { ToolID = "srvtoolu_SQfNkl1n_JR_" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaServerToolCaller { ToolID = "srvtoolu_SQfNkl1n_JR_" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedToolID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"code_execution_20250825\"" + ); + + Assert.Equal(expectedToolID, deserialized.ToolID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaServerToolCaller { ToolID = "srvtoolu_SQfNkl1n_JR_" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaServerToolUsageTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaServerToolUsageTest.cs new file mode 100644 index 00000000..e5f1c5ae --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaServerToolUsageTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaServerToolUsageTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaServerToolUsage { WebFetchRequests = 2, WebSearchRequests = 0 }; + + long expectedWebFetchRequests = 2; + long expectedWebSearchRequests = 0; + + Assert.Equal(expectedWebFetchRequests, model.WebFetchRequests); + Assert.Equal(expectedWebSearchRequests, model.WebSearchRequests); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaServerToolUsage { WebFetchRequests = 2, WebSearchRequests = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaServerToolUsage { WebFetchRequests = 2, WebSearchRequests = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedWebFetchRequests = 2; + long expectedWebSearchRequests = 0; + + Assert.Equal(expectedWebFetchRequests, deserialized.WebFetchRequests); + Assert.Equal(expectedWebSearchRequests, deserialized.WebSearchRequests); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaServerToolUsage { WebFetchRequests = 2, WebSearchRequests = 0 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaServerToolUseBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaServerToolUseBlockParamTest.cs new file mode 100644 index 00000000..5987199f --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaServerToolUseBlockParamTest.cs @@ -0,0 +1,347 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaServerToolUseBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = BetaServerToolUseBlockParamName.WebSearch, + CacheControl = new() { TTL = TTL.TTL5m }, + Caller = new BetaDirectCaller(), + }; + + string expectedID = "srvtoolu_SQfNkl1n_JR_"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + ApiEnum expectedName = + BetaServerToolUseBlockParamName.WebSearch; + JsonElement expectedType = JsonSerializer.Deserialize("\"server_tool_use\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + BetaServerToolUseBlockParamCaller expectedCaller = new BetaDirectCaller(); + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedInput.Count, model.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(model.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.Input[item.Key])); + } + Assert.Equal(expectedName, model.Name); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedCaller, model.Caller); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = BetaServerToolUseBlockParamName.WebSearch, + CacheControl = new() { TTL = TTL.TTL5m }, + Caller = new BetaDirectCaller(), + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = BetaServerToolUseBlockParamName.WebSearch, + CacheControl = new() { TTL = TTL.TTL5m }, + Caller = new BetaDirectCaller(), + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "srvtoolu_SQfNkl1n_JR_"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + ApiEnum expectedName = + BetaServerToolUseBlockParamName.WebSearch; + JsonElement expectedType = JsonSerializer.Deserialize("\"server_tool_use\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + BetaServerToolUseBlockParamCaller expectedCaller = new BetaDirectCaller(); + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedInput.Count, deserialized.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(deserialized.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.Input[item.Key])); + } + Assert.Equal(expectedName, deserialized.Name); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedCaller, deserialized.Caller); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = BetaServerToolUseBlockParamName.WebSearch, + CacheControl = new() { TTL = TTL.TTL5m }, + Caller = new BetaDirectCaller(), + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = BetaServerToolUseBlockParamName.WebSearch, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + Assert.Null(model.Caller); + Assert.False(model.RawData.ContainsKey("caller")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = BetaServerToolUseBlockParamName.WebSearch, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = BetaServerToolUseBlockParamName.WebSearch, + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + Caller = null, + }; + + Assert.Null(model.Caller); + Assert.False(model.RawData.ContainsKey("caller")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = BetaServerToolUseBlockParamName.WebSearch, + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + Caller = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = BetaServerToolUseBlockParamName.WebSearch, + Caller = new BetaDirectCaller(), + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = BetaServerToolUseBlockParamName.WebSearch, + Caller = new BetaDirectCaller(), + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = BetaServerToolUseBlockParamName.WebSearch, + Caller = new BetaDirectCaller(), + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = BetaServerToolUseBlockParamName.WebSearch, + Caller = new BetaDirectCaller(), + + CacheControl = null, + }; + + model.Validate(); + } +} + +public class BetaServerToolUseBlockParamNameTest : TestBase +{ + [Theory] + [InlineData(BetaServerToolUseBlockParamName.WebSearch)] + [InlineData(BetaServerToolUseBlockParamName.WebFetch)] + [InlineData(BetaServerToolUseBlockParamName.CodeExecution)] + [InlineData(BetaServerToolUseBlockParamName.BashCodeExecution)] + [InlineData(BetaServerToolUseBlockParamName.TextEditorCodeExecution)] + [InlineData(BetaServerToolUseBlockParamName.ToolSearchToolRegex)] + [InlineData(BetaServerToolUseBlockParamName.ToolSearchToolBm25)] + public void Validation_Works(BetaServerToolUseBlockParamName rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaServerToolUseBlockParamName.WebSearch)] + [InlineData(BetaServerToolUseBlockParamName.WebFetch)] + [InlineData(BetaServerToolUseBlockParamName.CodeExecution)] + [InlineData(BetaServerToolUseBlockParamName.BashCodeExecution)] + [InlineData(BetaServerToolUseBlockParamName.TextEditorCodeExecution)] + [InlineData(BetaServerToolUseBlockParamName.ToolSearchToolRegex)] + [InlineData(BetaServerToolUseBlockParamName.ToolSearchToolBm25)] + public void SerializationRoundtrip_Works(BetaServerToolUseBlockParamName rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaServerToolUseBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaServerToolUseBlockTest.cs new file mode 100644 index 00000000..fb52795a --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaServerToolUseBlockTest.cs @@ -0,0 +1,189 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaServerToolUseBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaServerToolUseBlock + { + ID = "srvtoolu_SQfNkl1n_JR_", + Caller = new BetaDirectCaller(), + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = Name.WebSearch, + }; + + string expectedID = "srvtoolu_SQfNkl1n_JR_"; + Caller expectedCaller = new BetaDirectCaller(); + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + ApiEnum expectedName = Name.WebSearch; + JsonElement expectedType = JsonSerializer.Deserialize("\"server_tool_use\""); + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedCaller, model.Caller); + Assert.Equal(expectedInput.Count, model.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(model.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.Input[item.Key])); + } + Assert.Equal(expectedName, model.Name); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaServerToolUseBlock + { + ID = "srvtoolu_SQfNkl1n_JR_", + Caller = new BetaDirectCaller(), + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = Name.WebSearch, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaServerToolUseBlock + { + ID = "srvtoolu_SQfNkl1n_JR_", + Caller = new BetaDirectCaller(), + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = Name.WebSearch, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "srvtoolu_SQfNkl1n_JR_"; + Caller expectedCaller = new BetaDirectCaller(); + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + ApiEnum expectedName = Name.WebSearch; + JsonElement expectedType = JsonSerializer.Deserialize("\"server_tool_use\""); + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedCaller, deserialized.Caller); + Assert.Equal(expectedInput.Count, deserialized.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(deserialized.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.Input[item.Key])); + } + Assert.Equal(expectedName, deserialized.Name); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaServerToolUseBlock + { + ID = "srvtoolu_SQfNkl1n_JR_", + Caller = new BetaDirectCaller(), + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = Name.WebSearch, + }; + + model.Validate(); + } +} + +public class NameTest : TestBase +{ + [Theory] + [InlineData(Name.WebSearch)] + [InlineData(Name.WebFetch)] + [InlineData(Name.CodeExecution)] + [InlineData(Name.BashCodeExecution)] + [InlineData(Name.TextEditorCodeExecution)] + [InlineData(Name.ToolSearchToolRegex)] + [InlineData(Name.ToolSearchToolBm25)] + public void Validation_Works(Name rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(Name.WebSearch)] + [InlineData(Name.WebFetch)] + [InlineData(Name.CodeExecution)] + [InlineData(Name.BashCodeExecution)] + [InlineData(Name.TextEditorCodeExecution)] + [InlineData(Name.ToolSearchToolRegex)] + [InlineData(Name.ToolSearchToolBm25)] + public void SerializationRoundtrip_Works(Name rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaSignatureDeltaTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaSignatureDeltaTest.cs new file mode 100644 index 00000000..b4e6555f --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaSignatureDeltaTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaSignatureDeltaTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaSignatureDelta { Signature = "signature" }; + + string expectedSignature = "signature"; + JsonElement expectedType = JsonSerializer.Deserialize("\"signature_delta\""); + + Assert.Equal(expectedSignature, model.Signature); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaSignatureDelta { Signature = "signature" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaSignatureDelta { Signature = "signature" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedSignature = "signature"; + JsonElement expectedType = JsonSerializer.Deserialize("\"signature_delta\""); + + Assert.Equal(expectedSignature, deserialized.Signature); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaSignatureDelta { Signature = "signature" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaSkillParamsTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaSkillParamsTest.cs new file mode 100644 index 00000000..02e8aa2f --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaSkillParamsTest.cs @@ -0,0 +1,184 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaSkillParamsTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaSkillParams + { + SkillID = "x", + Type = BetaSkillParamsType.Anthropic, + Version = "x", + }; + + string expectedSkillID = "x"; + ApiEnum expectedType = BetaSkillParamsType.Anthropic; + string expectedVersion = "x"; + + Assert.Equal(expectedSkillID, model.SkillID); + Assert.Equal(expectedType, model.Type); + Assert.Equal(expectedVersion, model.Version); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaSkillParams + { + SkillID = "x", + Type = BetaSkillParamsType.Anthropic, + Version = "x", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaSkillParams + { + SkillID = "x", + Type = BetaSkillParamsType.Anthropic, + Version = "x", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedSkillID = "x"; + ApiEnum expectedType = BetaSkillParamsType.Anthropic; + string expectedVersion = "x"; + + Assert.Equal(expectedSkillID, deserialized.SkillID); + Assert.Equal(expectedType, deserialized.Type); + Assert.Equal(expectedVersion, deserialized.Version); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaSkillParams + { + SkillID = "x", + Type = BetaSkillParamsType.Anthropic, + Version = "x", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaSkillParams { SkillID = "x", Type = BetaSkillParamsType.Anthropic }; + + Assert.Null(model.Version); + Assert.False(model.RawData.ContainsKey("version")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaSkillParams { SkillID = "x", Type = BetaSkillParamsType.Anthropic }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaSkillParams + { + SkillID = "x", + Type = BetaSkillParamsType.Anthropic, + + // Null should be interpreted as omitted for these properties + Version = null, + }; + + Assert.Null(model.Version); + Assert.False(model.RawData.ContainsKey("version")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaSkillParams + { + SkillID = "x", + Type = BetaSkillParamsType.Anthropic, + + // Null should be interpreted as omitted for these properties + Version = null, + }; + + model.Validate(); + } +} + +public class BetaSkillParamsTypeTest : TestBase +{ + [Theory] + [InlineData(BetaSkillParamsType.Anthropic)] + [InlineData(BetaSkillParamsType.Custom)] + public void Validation_Works(BetaSkillParamsType rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaSkillParamsType.Anthropic)] + [InlineData(BetaSkillParamsType.Custom)] + public void SerializationRoundtrip_Works(BetaSkillParamsType rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaSkillTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaSkillTest.cs new file mode 100644 index 00000000..f1f79fe1 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaSkillTest.cs @@ -0,0 +1,136 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaSkillTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaSkill + { + SkillID = "x", + Type = Type.Anthropic, + Version = "x", + }; + + string expectedSkillID = "x"; + ApiEnum expectedType = Type.Anthropic; + string expectedVersion = "x"; + + Assert.Equal(expectedSkillID, model.SkillID); + Assert.Equal(expectedType, model.Type); + Assert.Equal(expectedVersion, model.Version); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaSkill + { + SkillID = "x", + Type = Type.Anthropic, + Version = "x", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaSkill + { + SkillID = "x", + Type = Type.Anthropic, + Version = "x", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedSkillID = "x"; + ApiEnum expectedType = Type.Anthropic; + string expectedVersion = "x"; + + Assert.Equal(expectedSkillID, deserialized.SkillID); + Assert.Equal(expectedType, deserialized.Type); + Assert.Equal(expectedVersion, deserialized.Version); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaSkill + { + SkillID = "x", + Type = Type.Anthropic, + Version = "x", + }; + + model.Validate(); + } +} + +public class TypeTest : TestBase +{ + [Theory] + [InlineData(Type.Anthropic)] + [InlineData(Type.Custom)] + public void Validation_Works(Type rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(Type.Anthropic)] + [InlineData(Type.Custom)] + public void SerializationRoundtrip_Works(Type rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaStopReasonTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaStopReasonTest.cs new file mode 100644 index 00000000..9edcc655 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaStopReasonTest.cs @@ -0,0 +1,72 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaStopReasonTest : TestBase +{ + [Theory] + [InlineData(BetaStopReason.EndTurn)] + [InlineData(BetaStopReason.MaxTokens)] + [InlineData(BetaStopReason.StopSequence)] + [InlineData(BetaStopReason.ToolUse)] + [InlineData(BetaStopReason.PauseTurn)] + [InlineData(BetaStopReason.Refusal)] + [InlineData(BetaStopReason.ModelContextWindowExceeded)] + public void Validation_Works(BetaStopReason rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaStopReason.EndTurn)] + [InlineData(BetaStopReason.MaxTokens)] + [InlineData(BetaStopReason.StopSequence)] + [InlineData(BetaStopReason.ToolUse)] + [InlineData(BetaStopReason.PauseTurn)] + [InlineData(BetaStopReason.Refusal)] + [InlineData(BetaStopReason.ModelContextWindowExceeded)] + public void SerializationRoundtrip_Works(BetaStopReason rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaTextBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextBlockParamTest.cs new file mode 100644 index 00000000..5b574b4b --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextBlockParamTest.cs @@ -0,0 +1,201 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaTextBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaTextBlockParam + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }; + + string expectedText = "x"; + JsonElement expectedType = JsonSerializer.Deserialize("\"text\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + List expectedCitations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ]; + + Assert.Equal(expectedText, model.Text); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedCitations.Count, model.Citations.Count); + for (int i = 0; i < expectedCitations.Count; i++) + { + Assert.Equal(expectedCitations[i], model.Citations[i]); + } + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaTextBlockParam + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaTextBlockParam + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedText = "x"; + JsonElement expectedType = JsonSerializer.Deserialize("\"text\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + List expectedCitations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ]; + + Assert.Equal(expectedText, deserialized.Text); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedCitations.Count, deserialized.Citations.Count); + for (int i = 0; i < expectedCitations.Count; i++) + { + Assert.Equal(expectedCitations[i], deserialized.Citations[i]); + } + } + + [Fact] + public void Validation_Works() + { + var model = new BetaTextBlockParam + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new BetaCitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaTextBlockParam { Text = "x" }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Citations); + Assert.False(model.RawData.ContainsKey("citations")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaTextBlockParam { Text = "x" }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaTextBlockParam + { + Text = "x", + + CacheControl = null, + Citations = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Citations); + Assert.True(model.RawData.ContainsKey("citations")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaTextBlockParam + { + Text = "x", + + CacheControl = null, + Citations = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaTextBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextBlockTest.cs new file mode 100644 index 00000000..bbdeb997 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextBlockTest.cs @@ -0,0 +1,149 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaTextBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaTextBlock + { + Citations = + [ + new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }; + + List expectedCitations = + [ + new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ]; + string expectedText = "text"; + JsonElement expectedType = JsonSerializer.Deserialize("\"text\""); + + Assert.Equal(expectedCitations.Count, model.Citations.Count); + for (int i = 0; i < expectedCitations.Count; i++) + { + Assert.Equal(expectedCitations[i], model.Citations[i]); + } + Assert.Equal(expectedText, model.Text); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaTextBlock + { + Citations = + [ + new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaTextBlock + { + Citations = + [ + new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedCitations = + [ + new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ]; + string expectedText = "text"; + JsonElement expectedType = JsonSerializer.Deserialize("\"text\""); + + Assert.Equal(expectedCitations.Count, deserialized.Citations.Count); + for (int i = 0; i < expectedCitations.Count; i++) + { + Assert.Equal(expectedCitations[i], deserialized.Citations[i]); + } + Assert.Equal(expectedText, deserialized.Text); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaTextBlock + { + Citations = + [ + new BetaCitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaTextCitationParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextCitationParamTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextCitationParamTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaTextCitationTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextCitationTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextCitationTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaTextDeltaTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextDeltaTest.cs new file mode 100644 index 00000000..41a07429 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextDeltaTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaTextDeltaTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaTextDelta { Text = "text" }; + + string expectedText = "text"; + JsonElement expectedType = JsonSerializer.Deserialize("\"text_delta\""); + + Assert.Equal(expectedText, model.Text); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaTextDelta { Text = "text" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaTextDelta { Text = "text" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedText = "text"; + JsonElement expectedType = JsonSerializer.Deserialize("\"text_delta\""); + + Assert.Equal(expectedText, deserialized.Text); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaTextDelta { Text = "text" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionCreateResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionCreateResultBlockParamTest.cs new file mode 100644 index 00000000..70514259 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionCreateResultBlockParamTest.cs @@ -0,0 +1,60 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaTextEditorCodeExecutionCreateResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionCreateResultBlockParam { IsFileUpdate = true }; + + bool expectedIsFileUpdate = true; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_create_result\"" + ); + + Assert.Equal(expectedIsFileUpdate, model.IsFileUpdate); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionCreateResultBlockParam { IsFileUpdate = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = + JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaTextEditorCodeExecutionCreateResultBlockParam { IsFileUpdate = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = + JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + bool expectedIsFileUpdate = true; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_create_result\"" + ); + + Assert.Equal(expectedIsFileUpdate, deserialized.IsFileUpdate); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaTextEditorCodeExecutionCreateResultBlockParam { IsFileUpdate = true }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionCreateResultBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionCreateResultBlockTest.cs new file mode 100644 index 00000000..2bc2be81 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionCreateResultBlockTest.cs @@ -0,0 +1,62 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaTextEditorCodeExecutionCreateResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionCreateResultBlock { IsFileUpdate = true }; + + bool expectedIsFileUpdate = true; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_create_result\"" + ); + + Assert.Equal(expectedIsFileUpdate, model.IsFileUpdate); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionCreateResultBlock { IsFileUpdate = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaTextEditorCodeExecutionCreateResultBlock { IsFileUpdate = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + Assert.NotNull(deserialized); + + bool expectedIsFileUpdate = true; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_create_result\"" + ); + + Assert.Equal(expectedIsFileUpdate, deserialized.IsFileUpdate); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaTextEditorCodeExecutionCreateResultBlock { IsFileUpdate = true }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionStrReplaceResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionStrReplaceResultBlockParamTest.cs new file mode 100644 index 00000000..4dd1761b --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionStrReplaceResultBlockParamTest.cs @@ -0,0 +1,177 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaTextEditorCodeExecutionStrReplaceResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionStrReplaceResultBlockParam + { + Lines = ["string"], + NewLines = 0, + NewStart = 0, + OldLines = 0, + OldStart = 0, + }; + + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_str_replace_result\"" + ); + List expectedLines = ["string"]; + long expectedNewLines = 0; + long expectedNewStart = 0; + long expectedOldLines = 0; + long expectedOldStart = 0; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedLines.Count, model.Lines.Count); + for (int i = 0; i < expectedLines.Count; i++) + { + Assert.Equal(expectedLines[i], model.Lines[i]); + } + Assert.Equal(expectedNewLines, model.NewLines); + Assert.Equal(expectedNewStart, model.NewStart); + Assert.Equal(expectedOldLines, model.OldLines); + Assert.Equal(expectedOldStart, model.OldStart); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionStrReplaceResultBlockParam + { + Lines = ["string"], + NewLines = 0, + NewStart = 0, + OldLines = 0, + OldStart = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = + JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaTextEditorCodeExecutionStrReplaceResultBlockParam + { + Lines = ["string"], + NewLines = 0, + NewStart = 0, + OldLines = 0, + OldStart = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = + JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_str_replace_result\"" + ); + List expectedLines = ["string"]; + long expectedNewLines = 0; + long expectedNewStart = 0; + long expectedOldLines = 0; + long expectedOldStart = 0; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedLines.Count, deserialized.Lines.Count); + for (int i = 0; i < expectedLines.Count; i++) + { + Assert.Equal(expectedLines[i], deserialized.Lines[i]); + } + Assert.Equal(expectedNewLines, deserialized.NewLines); + Assert.Equal(expectedNewStart, deserialized.NewStart); + Assert.Equal(expectedOldLines, deserialized.OldLines); + Assert.Equal(expectedOldStart, deserialized.OldStart); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaTextEditorCodeExecutionStrReplaceResultBlockParam + { + Lines = ["string"], + NewLines = 0, + NewStart = 0, + OldLines = 0, + OldStart = 0, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaTextEditorCodeExecutionStrReplaceResultBlockParam { }; + + Assert.Null(model.Lines); + Assert.False(model.RawData.ContainsKey("lines")); + Assert.Null(model.NewLines); + Assert.False(model.RawData.ContainsKey("new_lines")); + Assert.Null(model.NewStart); + Assert.False(model.RawData.ContainsKey("new_start")); + Assert.Null(model.OldLines); + Assert.False(model.RawData.ContainsKey("old_lines")); + Assert.Null(model.OldStart); + Assert.False(model.RawData.ContainsKey("old_start")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaTextEditorCodeExecutionStrReplaceResultBlockParam { }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaTextEditorCodeExecutionStrReplaceResultBlockParam + { + Lines = null, + NewLines = null, + NewStart = null, + OldLines = null, + OldStart = null, + }; + + Assert.Null(model.Lines); + Assert.True(model.RawData.ContainsKey("lines")); + Assert.Null(model.NewLines); + Assert.True(model.RawData.ContainsKey("new_lines")); + Assert.Null(model.NewStart); + Assert.True(model.RawData.ContainsKey("new_start")); + Assert.Null(model.OldLines); + Assert.True(model.RawData.ContainsKey("old_lines")); + Assert.Null(model.OldStart); + Assert.True(model.RawData.ContainsKey("old_start")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaTextEditorCodeExecutionStrReplaceResultBlockParam + { + Lines = null, + NewLines = null, + NewStart = null, + OldLines = null, + OldStart = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionStrReplaceResultBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionStrReplaceResultBlockTest.cs new file mode 100644 index 00000000..e5589593 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionStrReplaceResultBlockTest.cs @@ -0,0 +1,113 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaTextEditorCodeExecutionStrReplaceResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionStrReplaceResultBlock + { + Lines = ["string"], + NewLines = 0, + NewStart = 0, + OldLines = 0, + OldStart = 0, + }; + + List expectedLines = ["string"]; + long expectedNewLines = 0; + long expectedNewStart = 0; + long expectedOldLines = 0; + long expectedOldStart = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_str_replace_result\"" + ); + + Assert.Equal(expectedLines.Count, model.Lines.Count); + for (int i = 0; i < expectedLines.Count; i++) + { + Assert.Equal(expectedLines[i], model.Lines[i]); + } + Assert.Equal(expectedNewLines, model.NewLines); + Assert.Equal(expectedNewStart, model.NewStart); + Assert.Equal(expectedOldLines, model.OldLines); + Assert.Equal(expectedOldStart, model.OldStart); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionStrReplaceResultBlock + { + Lines = ["string"], + NewLines = 0, + NewStart = 0, + OldLines = 0, + OldStart = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = + JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaTextEditorCodeExecutionStrReplaceResultBlock + { + Lines = ["string"], + NewLines = 0, + NewStart = 0, + OldLines = 0, + OldStart = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = + JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedLines = ["string"]; + long expectedNewLines = 0; + long expectedNewStart = 0; + long expectedOldLines = 0; + long expectedOldStart = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_str_replace_result\"" + ); + + Assert.Equal(expectedLines.Count, deserialized.Lines.Count); + for (int i = 0; i < expectedLines.Count; i++) + { + Assert.Equal(expectedLines[i], deserialized.Lines[i]); + } + Assert.Equal(expectedNewLines, deserialized.NewLines); + Assert.Equal(expectedNewStart, deserialized.NewStart); + Assert.Equal(expectedOldLines, deserialized.OldLines); + Assert.Equal(expectedOldStart, deserialized.OldStart); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaTextEditorCodeExecutionStrReplaceResultBlock + { + Lines = ["string"], + NewLines = 0, + NewStart = 0, + OldLines = 0, + OldStart = 0, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultBlockParamTest.cs new file mode 100644 index 00000000..da02204e --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultBlockParamTest.cs @@ -0,0 +1,194 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaTextEditorCodeExecutionToolResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultBlockParam + { + Content = new BetaTextEditorCodeExecutionToolResultErrorParam() + { + ErrorCode = + BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + BetaTextEditorCodeExecutionToolResultBlockParamContent expectedContent = + new BetaTextEditorCodeExecutionToolResultErrorParam() + { + ErrorCode = + BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_tool_result\"" + ); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultBlockParam + { + Content = new BetaTextEditorCodeExecutionToolResultErrorParam() + { + ErrorCode = + BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = + JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultBlockParam + { + Content = new BetaTextEditorCodeExecutionToolResultErrorParam() + { + ErrorCode = + BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = + JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaTextEditorCodeExecutionToolResultBlockParamContent expectedContent = + new BetaTextEditorCodeExecutionToolResultErrorParam() + { + ErrorCode = + BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_tool_result\"" + ); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultBlockParam + { + Content = new BetaTextEditorCodeExecutionToolResultErrorParam() + { + ErrorCode = + BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultBlockParam + { + Content = new BetaTextEditorCodeExecutionToolResultErrorParam() + { + ErrorCode = + BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultBlockParam + { + Content = new BetaTextEditorCodeExecutionToolResultErrorParam() + { + ErrorCode = + BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultBlockParam + { + Content = new BetaTextEditorCodeExecutionToolResultErrorParam() + { + ErrorCode = + BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultBlockParam + { + Content = new BetaTextEditorCodeExecutionToolResultErrorParam() + { + ErrorCode = + BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultBlockTest.cs new file mode 100644 index 00000000..4acc033a --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultBlockTest.cs @@ -0,0 +1,108 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaTextEditorCodeExecutionToolResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultBlock + { + Content = new BetaTextEditorCodeExecutionToolResultError() + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + BetaTextEditorCodeExecutionToolResultBlockContent expectedContent = + new BetaTextEditorCodeExecutionToolResultError() + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_tool_result\"" + ); + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultBlock + { + Content = new BetaTextEditorCodeExecutionToolResultError() + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultBlock + { + Content = new BetaTextEditorCodeExecutionToolResultError() + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + Assert.NotNull(deserialized); + + BetaTextEditorCodeExecutionToolResultBlockContent expectedContent = + new BetaTextEditorCodeExecutionToolResultError() + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_tool_result\"" + ); + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultBlock + { + Content = new BetaTextEditorCodeExecutionToolResultError() + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultErrorParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultErrorParamTest.cs new file mode 100644 index 00000000..4cb09721 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultErrorParamTest.cs @@ -0,0 +1,206 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaTextEditorCodeExecutionToolResultErrorParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultErrorParam + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + + ApiEnum< + string, + BetaTextEditorCodeExecutionToolResultErrorParamErrorCode + > expectedErrorCode = + BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_tool_result_error\"" + ); + string expectedErrorMessage = "error_message"; + + Assert.Equal(expectedErrorCode, model.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedErrorMessage, model.ErrorMessage); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultErrorParam + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = + JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultErrorParam + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = + JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ApiEnum< + string, + BetaTextEditorCodeExecutionToolResultErrorParamErrorCode + > expectedErrorCode = + BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_tool_result_error\"" + ); + string expectedErrorMessage = "error_message"; + + Assert.Equal(expectedErrorCode, deserialized.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedErrorMessage, deserialized.ErrorMessage); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultErrorParam + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultErrorParam + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + }; + + Assert.Null(model.ErrorMessage); + Assert.False(model.RawData.ContainsKey("error_message")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultErrorParam + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultErrorParam + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + + ErrorMessage = null, + }; + + Assert.Null(model.ErrorMessage); + Assert.True(model.RawData.ContainsKey("error_message")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultErrorParam + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput, + + ErrorMessage = null, + }; + + model.Validate(); + } +} + +public class BetaTextEditorCodeExecutionToolResultErrorParamErrorCodeTest : TestBase +{ + [Theory] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.Unavailable)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.TooManyRequests)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.ExecutionTimeExceeded)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.FileNotFound)] + public void Validation_Works(BetaTextEditorCodeExecutionToolResultErrorParamErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.InvalidToolInput)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.Unavailable)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.TooManyRequests)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.ExecutionTimeExceeded)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorParamErrorCode.FileNotFound)] + public void SerializationRoundtrip_Works( + BetaTextEditorCodeExecutionToolResultErrorParamErrorCode rawValue + ) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultErrorTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultErrorTest.cs new file mode 100644 index 00000000..1fe2da4e --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultErrorTest.cs @@ -0,0 +1,152 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaTextEditorCodeExecutionToolResultErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultError + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + + ApiEnum expectedErrorCode = + BetaTextEditorCodeExecutionToolResultErrorErrorCode.InvalidToolInput; + string expectedErrorMessage = "error_message"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, model.ErrorCode); + Assert.Equal(expectedErrorMessage, model.ErrorMessage); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultError + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultError + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + Assert.NotNull(deserialized); + + ApiEnum expectedErrorCode = + BetaTextEditorCodeExecutionToolResultErrorErrorCode.InvalidToolInput; + string expectedErrorMessage = "error_message"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, deserialized.ErrorCode); + Assert.Equal(expectedErrorMessage, deserialized.ErrorMessage); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaTextEditorCodeExecutionToolResultError + { + ErrorCode = BetaTextEditorCodeExecutionToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + + model.Validate(); + } +} + +public class BetaTextEditorCodeExecutionToolResultErrorErrorCodeTest : TestBase +{ + [Theory] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorErrorCode.InvalidToolInput)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorErrorCode.Unavailable)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorErrorCode.TooManyRequests)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorErrorCode.ExecutionTimeExceeded)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorErrorCode.FileNotFound)] + public void Validation_Works(BetaTextEditorCodeExecutionToolResultErrorErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorErrorCode.InvalidToolInput)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorErrorCode.Unavailable)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorErrorCode.TooManyRequests)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorErrorCode.ExecutionTimeExceeded)] + [InlineData(BetaTextEditorCodeExecutionToolResultErrorErrorCode.FileNotFound)] + public void SerializationRoundtrip_Works( + BetaTextEditorCodeExecutionToolResultErrorErrorCode rawValue + ) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionViewResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionViewResultBlockParamTest.cs new file mode 100644 index 00000000..6c114aec --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionViewResultBlockParamTest.cs @@ -0,0 +1,236 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaTextEditorCodeExecutionViewResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionViewResultBlockParam + { + Content = "content", + FileType = BetaTextEditorCodeExecutionViewResultBlockParamFileType.Text, + NumLines = 0, + StartLine = 0, + TotalLines = 0, + }; + + string expectedContent = "content"; + ApiEnum expectedFileType = + BetaTextEditorCodeExecutionViewResultBlockParamFileType.Text; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_view_result\"" + ); + long expectedNumLines = 0; + long expectedStartLine = 0; + long expectedTotalLines = 0; + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedFileType, model.FileType); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedNumLines, model.NumLines); + Assert.Equal(expectedStartLine, model.StartLine); + Assert.Equal(expectedTotalLines, model.TotalLines); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionViewResultBlockParam + { + Content = "content", + FileType = BetaTextEditorCodeExecutionViewResultBlockParamFileType.Text, + NumLines = 0, + StartLine = 0, + TotalLines = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = + JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaTextEditorCodeExecutionViewResultBlockParam + { + Content = "content", + FileType = BetaTextEditorCodeExecutionViewResultBlockParamFileType.Text, + NumLines = 0, + StartLine = 0, + TotalLines = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = + JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedContent = "content"; + ApiEnum expectedFileType = + BetaTextEditorCodeExecutionViewResultBlockParamFileType.Text; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_view_result\"" + ); + long expectedNumLines = 0; + long expectedStartLine = 0; + long expectedTotalLines = 0; + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedFileType, deserialized.FileType); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedNumLines, deserialized.NumLines); + Assert.Equal(expectedStartLine, deserialized.StartLine); + Assert.Equal(expectedTotalLines, deserialized.TotalLines); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaTextEditorCodeExecutionViewResultBlockParam + { + Content = "content", + FileType = BetaTextEditorCodeExecutionViewResultBlockParamFileType.Text, + NumLines = 0, + StartLine = 0, + TotalLines = 0, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaTextEditorCodeExecutionViewResultBlockParam + { + Content = "content", + FileType = BetaTextEditorCodeExecutionViewResultBlockParamFileType.Text, + }; + + Assert.Null(model.NumLines); + Assert.False(model.RawData.ContainsKey("num_lines")); + Assert.Null(model.StartLine); + Assert.False(model.RawData.ContainsKey("start_line")); + Assert.Null(model.TotalLines); + Assert.False(model.RawData.ContainsKey("total_lines")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaTextEditorCodeExecutionViewResultBlockParam + { + Content = "content", + FileType = BetaTextEditorCodeExecutionViewResultBlockParamFileType.Text, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaTextEditorCodeExecutionViewResultBlockParam + { + Content = "content", + FileType = BetaTextEditorCodeExecutionViewResultBlockParamFileType.Text, + + NumLines = null, + StartLine = null, + TotalLines = null, + }; + + Assert.Null(model.NumLines); + Assert.True(model.RawData.ContainsKey("num_lines")); + Assert.Null(model.StartLine); + Assert.True(model.RawData.ContainsKey("start_line")); + Assert.Null(model.TotalLines); + Assert.True(model.RawData.ContainsKey("total_lines")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaTextEditorCodeExecutionViewResultBlockParam + { + Content = "content", + FileType = BetaTextEditorCodeExecutionViewResultBlockParamFileType.Text, + + NumLines = null, + StartLine = null, + TotalLines = null, + }; + + model.Validate(); + } +} + +public class BetaTextEditorCodeExecutionViewResultBlockParamFileTypeTest : TestBase +{ + [Theory] + [InlineData(BetaTextEditorCodeExecutionViewResultBlockParamFileType.Text)] + [InlineData(BetaTextEditorCodeExecutionViewResultBlockParamFileType.Image)] + [InlineData(BetaTextEditorCodeExecutionViewResultBlockParamFileType.PDF)] + public void Validation_Works(BetaTextEditorCodeExecutionViewResultBlockParamFileType rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaTextEditorCodeExecutionViewResultBlockParamFileType.Text)] + [InlineData(BetaTextEditorCodeExecutionViewResultBlockParamFileType.Image)] + [InlineData(BetaTextEditorCodeExecutionViewResultBlockParamFileType.PDF)] + public void SerializationRoundtrip_Works( + BetaTextEditorCodeExecutionViewResultBlockParamFileType rawValue + ) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionViewResultBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionViewResultBlockTest.cs new file mode 100644 index 00000000..948f7e73 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaTextEditorCodeExecutionViewResultBlockTest.cs @@ -0,0 +1,166 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaTextEditorCodeExecutionViewResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionViewResultBlock + { + Content = "content", + FileType = FileType.Text, + NumLines = 0, + StartLine = 0, + TotalLines = 0, + }; + + string expectedContent = "content"; + ApiEnum expectedFileType = FileType.Text; + long expectedNumLines = 0; + long expectedStartLine = 0; + long expectedTotalLines = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_view_result\"" + ); + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedFileType, model.FileType); + Assert.Equal(expectedNumLines, model.NumLines); + Assert.Equal(expectedStartLine, model.StartLine); + Assert.Equal(expectedTotalLines, model.TotalLines); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaTextEditorCodeExecutionViewResultBlock + { + Content = "content", + FileType = FileType.Text, + NumLines = 0, + StartLine = 0, + TotalLines = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaTextEditorCodeExecutionViewResultBlock + { + Content = "content", + FileType = FileType.Text, + NumLines = 0, + StartLine = 0, + TotalLines = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + Assert.NotNull(deserialized); + + string expectedContent = "content"; + ApiEnum expectedFileType = FileType.Text; + long expectedNumLines = 0; + long expectedStartLine = 0; + long expectedTotalLines = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_code_execution_view_result\"" + ); + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedFileType, deserialized.FileType); + Assert.Equal(expectedNumLines, deserialized.NumLines); + Assert.Equal(expectedStartLine, deserialized.StartLine); + Assert.Equal(expectedTotalLines, deserialized.TotalLines); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaTextEditorCodeExecutionViewResultBlock + { + Content = "content", + FileType = FileType.Text, + NumLines = 0, + StartLine = 0, + TotalLines = 0, + }; + + model.Validate(); + } +} + +public class FileTypeTest : TestBase +{ + [Theory] + [InlineData(FileType.Text)] + [InlineData(FileType.Image)] + [InlineData(FileType.PDF)] + public void Validation_Works(FileType rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(FileType.Text)] + [InlineData(FileType.Image)] + [InlineData(FileType.PDF)] + public void SerializationRoundtrip_Works(FileType rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingBlockParamTest.cs new file mode 100644 index 00000000..1ad1cfec --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingBlockParamTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaThinkingBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaThinkingBlockParam { Signature = "signature", Thinking = "thinking" }; + + string expectedSignature = "signature"; + string expectedThinking = "thinking"; + JsonElement expectedType = JsonSerializer.Deserialize("\"thinking\""); + + Assert.Equal(expectedSignature, model.Signature); + Assert.Equal(expectedThinking, model.Thinking); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaThinkingBlockParam { Signature = "signature", Thinking = "thinking" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaThinkingBlockParam { Signature = "signature", Thinking = "thinking" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedSignature = "signature"; + string expectedThinking = "thinking"; + JsonElement expectedType = JsonSerializer.Deserialize("\"thinking\""); + + Assert.Equal(expectedSignature, deserialized.Signature); + Assert.Equal(expectedThinking, deserialized.Thinking); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaThinkingBlockParam { Signature = "signature", Thinking = "thinking" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingBlockTest.cs new file mode 100644 index 00000000..a65a7b72 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingBlockTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaThinkingBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaThinkingBlock { Signature = "signature", Thinking = "thinking" }; + + string expectedSignature = "signature"; + string expectedThinking = "thinking"; + JsonElement expectedType = JsonSerializer.Deserialize("\"thinking\""); + + Assert.Equal(expectedSignature, model.Signature); + Assert.Equal(expectedThinking, model.Thinking); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaThinkingBlock { Signature = "signature", Thinking = "thinking" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaThinkingBlock { Signature = "signature", Thinking = "thinking" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedSignature = "signature"; + string expectedThinking = "thinking"; + JsonElement expectedType = JsonSerializer.Deserialize("\"thinking\""); + + Assert.Equal(expectedSignature, deserialized.Signature); + Assert.Equal(expectedThinking, deserialized.Thinking); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaThinkingBlock { Signature = "signature", Thinking = "thinking" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingConfigDisabledTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingConfigDisabledTest.cs new file mode 100644 index 00000000..cb9a825c --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingConfigDisabledTest.cs @@ -0,0 +1,50 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaThinkingConfigDisabledTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaThinkingConfigDisabled { }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"disabled\""); + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaThinkingConfigDisabled { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaThinkingConfigDisabled { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"disabled\""); + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaThinkingConfigDisabled { }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingConfigEnabledTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingConfigEnabledTest.cs new file mode 100644 index 00000000..ade92746 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingConfigEnabledTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaThinkingConfigEnabledTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaThinkingConfigEnabled { BudgetTokens = 1024 }; + + long expectedBudgetTokens = 1024; + JsonElement expectedType = JsonSerializer.Deserialize("\"enabled\""); + + Assert.Equal(expectedBudgetTokens, model.BudgetTokens); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaThinkingConfigEnabled { BudgetTokens = 1024 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaThinkingConfigEnabled { BudgetTokens = 1024 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedBudgetTokens = 1024; + JsonElement expectedType = JsonSerializer.Deserialize("\"enabled\""); + + Assert.Equal(expectedBudgetTokens, deserialized.BudgetTokens); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaThinkingConfigEnabled { BudgetTokens = 1024 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingConfigParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingConfigParamTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingConfigParamTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingDeltaTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingDeltaTest.cs new file mode 100644 index 00000000..7c8018bf --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingDeltaTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaThinkingDeltaTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaThinkingDelta { Thinking = "thinking" }; + + string expectedThinking = "thinking"; + JsonElement expectedType = JsonSerializer.Deserialize("\"thinking_delta\""); + + Assert.Equal(expectedThinking, model.Thinking); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaThinkingDelta { Thinking = "thinking" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaThinkingDelta { Thinking = "thinking" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedThinking = "thinking"; + JsonElement expectedType = JsonSerializer.Deserialize("\"thinking_delta\""); + + Assert.Equal(expectedThinking, deserialized.Thinking); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaThinkingDelta { Thinking = "thinking" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingTurnsTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingTurnsTest.cs new file mode 100644 index 00000000..726a07ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaThinkingTurnsTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaThinkingTurnsTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaThinkingTurns { Value = 1 }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"thinking_turns\""); + long expectedValue = 1; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedValue, model.Value); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaThinkingTurns { Value = 1 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaThinkingTurns { Value = 1 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"thinking_turns\""); + long expectedValue = 1; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedValue, deserialized.Value); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaThinkingTurns { Value = 1 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolBash20241022Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolBash20241022Test.cs new file mode 100644 index 00000000..d6151ae5 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolBash20241022Test.cs @@ -0,0 +1,379 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolBash20241022Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolBash20241022 + { + AllowedCallers = [BetaToolBash20241022AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + JsonElement expectedName = JsonSerializer.Deserialize("\"bash\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"bash_20241022\""); + List> expectedAllowedCallers = + [ + BetaToolBash20241022AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedInputExamples.Count, model.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, model.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(model.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, model.Strict); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolBash20241022 + { + AllowedCallers = [BetaToolBash20241022AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolBash20241022 + { + AllowedCallers = [BetaToolBash20241022AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize("\"bash\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"bash_20241022\""); + List> expectedAllowedCallers = + [ + BetaToolBash20241022AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedInputExamples.Count, deserialized.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, deserialized.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(deserialized.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, deserialized.Strict); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolBash20241022 + { + AllowedCallers = [BetaToolBash20241022AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolBash20241022 { CacheControl = new() { TTL = TTL.TTL5m } }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolBash20241022 { CacheControl = new() { TTL = TTL.TTL5m } }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolBash20241022 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolBash20241022 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolBash20241022 + { + AllowedCallers = [BetaToolBash20241022AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolBash20241022 + { + AllowedCallers = [BetaToolBash20241022AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaToolBash20241022 + { + AllowedCallers = [BetaToolBash20241022AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolBash20241022 + { + AllowedCallers = [BetaToolBash20241022AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + }; + + model.Validate(); + } +} + +public class BetaToolBash20241022AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaToolBash20241022AllowedCaller.Direct)] + [InlineData(BetaToolBash20241022AllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaToolBash20241022AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolBash20241022AllowedCaller.Direct)] + [InlineData(BetaToolBash20241022AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaToolBash20241022AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolBash20250124Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolBash20250124Test.cs new file mode 100644 index 00000000..23c5e413 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolBash20250124Test.cs @@ -0,0 +1,379 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolBash20250124Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolBash20250124 + { + AllowedCallers = [BetaToolBash20250124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + JsonElement expectedName = JsonSerializer.Deserialize("\"bash\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"bash_20250124\""); + List> expectedAllowedCallers = + [ + BetaToolBash20250124AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedInputExamples.Count, model.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, model.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(model.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, model.Strict); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolBash20250124 + { + AllowedCallers = [BetaToolBash20250124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolBash20250124 + { + AllowedCallers = [BetaToolBash20250124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize("\"bash\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"bash_20250124\""); + List> expectedAllowedCallers = + [ + BetaToolBash20250124AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedInputExamples.Count, deserialized.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, deserialized.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(deserialized.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, deserialized.Strict); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolBash20250124 + { + AllowedCallers = [BetaToolBash20250124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolBash20250124 { CacheControl = new() { TTL = TTL.TTL5m } }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolBash20250124 { CacheControl = new() { TTL = TTL.TTL5m } }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolBash20250124 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolBash20250124 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolBash20250124 + { + AllowedCallers = [BetaToolBash20250124AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolBash20250124 + { + AllowedCallers = [BetaToolBash20250124AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaToolBash20250124 + { + AllowedCallers = [BetaToolBash20250124AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolBash20250124 + { + AllowedCallers = [BetaToolBash20250124AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + }; + + model.Validate(); + } +} + +public class BetaToolBash20250124AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaToolBash20250124AllowedCaller.Direct)] + [InlineData(BetaToolBash20250124AllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaToolBash20250124AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolBash20250124AllowedCaller.Direct)] + [InlineData(BetaToolBash20250124AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaToolBash20250124AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolChoiceAnyTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolChoiceAnyTest.cs new file mode 100644 index 00000000..dec06fb2 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolChoiceAnyTest.cs @@ -0,0 +1,96 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolChoiceAnyTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolChoiceAny { DisableParallelToolUse = true }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"any\""); + bool expectedDisableParallelToolUse = true; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedDisableParallelToolUse, model.DisableParallelToolUse); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolChoiceAny { DisableParallelToolUse = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolChoiceAny { DisableParallelToolUse = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"any\""); + bool expectedDisableParallelToolUse = true; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedDisableParallelToolUse, deserialized.DisableParallelToolUse); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolChoiceAny { DisableParallelToolUse = true }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolChoiceAny { }; + + Assert.Null(model.DisableParallelToolUse); + Assert.False(model.RawData.ContainsKey("disable_parallel_tool_use")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolChoiceAny { }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolChoiceAny + { + // Null should be interpreted as omitted for these properties + DisableParallelToolUse = null, + }; + + Assert.Null(model.DisableParallelToolUse); + Assert.False(model.RawData.ContainsKey("disable_parallel_tool_use")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolChoiceAny + { + // Null should be interpreted as omitted for these properties + DisableParallelToolUse = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolChoiceAutoTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolChoiceAutoTest.cs new file mode 100644 index 00000000..45cd55ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolChoiceAutoTest.cs @@ -0,0 +1,96 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolChoiceAutoTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolChoiceAuto { DisableParallelToolUse = true }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"auto\""); + bool expectedDisableParallelToolUse = true; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedDisableParallelToolUse, model.DisableParallelToolUse); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolChoiceAuto { DisableParallelToolUse = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolChoiceAuto { DisableParallelToolUse = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"auto\""); + bool expectedDisableParallelToolUse = true; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedDisableParallelToolUse, deserialized.DisableParallelToolUse); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolChoiceAuto { DisableParallelToolUse = true }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolChoiceAuto { }; + + Assert.Null(model.DisableParallelToolUse); + Assert.False(model.RawData.ContainsKey("disable_parallel_tool_use")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolChoiceAuto { }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolChoiceAuto + { + // Null should be interpreted as omitted for these properties + DisableParallelToolUse = null, + }; + + Assert.Null(model.DisableParallelToolUse); + Assert.False(model.RawData.ContainsKey("disable_parallel_tool_use")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolChoiceAuto + { + // Null should be interpreted as omitted for these properties + DisableParallelToolUse = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolChoiceNoneTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolChoiceNoneTest.cs new file mode 100644 index 00000000..70e77bd8 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolChoiceNoneTest.cs @@ -0,0 +1,50 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolChoiceNoneTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolChoiceNone { }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"none\""); + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolChoiceNone { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolChoiceNone { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"none\""); + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolChoiceNone { }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolChoiceTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolChoiceTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolChoiceTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolChoiceToolTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolChoiceToolTest.cs new file mode 100644 index 00000000..b3d2f157 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolChoiceToolTest.cs @@ -0,0 +1,104 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolChoiceToolTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolChoiceTool { Name = "name", DisableParallelToolUse = true }; + + string expectedName = "name"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool\""); + bool expectedDisableParallelToolUse = true; + + Assert.Equal(expectedName, model.Name); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedDisableParallelToolUse, model.DisableParallelToolUse); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolChoiceTool { Name = "name", DisableParallelToolUse = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolChoiceTool { Name = "name", DisableParallelToolUse = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedName = "name"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool\""); + bool expectedDisableParallelToolUse = true; + + Assert.Equal(expectedName, deserialized.Name); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedDisableParallelToolUse, deserialized.DisableParallelToolUse); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolChoiceTool { Name = "name", DisableParallelToolUse = true }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolChoiceTool { Name = "name" }; + + Assert.Null(model.DisableParallelToolUse); + Assert.False(model.RawData.ContainsKey("disable_parallel_tool_use")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolChoiceTool { Name = "name" }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolChoiceTool + { + Name = "name", + + // Null should be interpreted as omitted for these properties + DisableParallelToolUse = null, + }; + + Assert.Null(model.DisableParallelToolUse); + Assert.False(model.RawData.ContainsKey("disable_parallel_tool_use")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolChoiceTool + { + Name = "name", + + // Null should be interpreted as omitted for these properties + DisableParallelToolUse = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolComputerUse20241022Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolComputerUse20241022Test.cs new file mode 100644 index 00000000..cef86104 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolComputerUse20241022Test.cs @@ -0,0 +1,439 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolComputerUse20241022Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolComputerUse20241022 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20241022AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + DisplayNumber = 0, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + long expectedDisplayHeightPx = 1; + long expectedDisplayWidthPx = 1; + JsonElement expectedName = JsonSerializer.Deserialize("\"computer\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"computer_20241022\""); + List> expectedAllowedCallers = + [ + BetaToolComputerUse20241022AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + long expectedDisplayNumber = 0; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.Equal(expectedDisplayHeightPx, model.DisplayHeightPx); + Assert.Equal(expectedDisplayWidthPx, model.DisplayWidthPx); + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedDisplayNumber, model.DisplayNumber); + Assert.Equal(expectedInputExamples.Count, model.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, model.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(model.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, model.Strict); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolComputerUse20241022 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20241022AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + DisplayNumber = 0, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolComputerUse20241022 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20241022AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + DisplayNumber = 0, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedDisplayHeightPx = 1; + long expectedDisplayWidthPx = 1; + JsonElement expectedName = JsonSerializer.Deserialize("\"computer\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"computer_20241022\""); + List> expectedAllowedCallers = + [ + BetaToolComputerUse20241022AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + long expectedDisplayNumber = 0; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.Equal(expectedDisplayHeightPx, deserialized.DisplayHeightPx); + Assert.Equal(expectedDisplayWidthPx, deserialized.DisplayWidthPx); + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedDisplayNumber, deserialized.DisplayNumber); + Assert.Equal(expectedInputExamples.Count, deserialized.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, deserialized.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(deserialized.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, deserialized.Strict); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolComputerUse20241022 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20241022AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + DisplayNumber = 0, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolComputerUse20241022 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + CacheControl = new() { TTL = TTL.TTL5m }, + DisplayNumber = 0, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolComputerUse20241022 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + CacheControl = new() { TTL = TTL.TTL5m }, + DisplayNumber = 0, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolComputerUse20241022 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + CacheControl = new() { TTL = TTL.TTL5m }, + DisplayNumber = 0, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolComputerUse20241022 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + CacheControl = new() { TTL = TTL.TTL5m }, + DisplayNumber = 0, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolComputerUse20241022 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20241022AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.DisplayNumber); + Assert.False(model.RawData.ContainsKey("display_number")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolComputerUse20241022 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20241022AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaToolComputerUse20241022 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20241022AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + DisplayNumber = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.DisplayNumber); + Assert.True(model.RawData.ContainsKey("display_number")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolComputerUse20241022 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20241022AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + DisplayNumber = null, + }; + + model.Validate(); + } +} + +public class BetaToolComputerUse20241022AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaToolComputerUse20241022AllowedCaller.Direct)] + [InlineData(BetaToolComputerUse20241022AllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaToolComputerUse20241022AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolComputerUse20241022AllowedCaller.Direct)] + [InlineData(BetaToolComputerUse20241022AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaToolComputerUse20241022AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolComputerUse20250124Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolComputerUse20250124Test.cs new file mode 100644 index 00000000..6a8df3a9 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolComputerUse20250124Test.cs @@ -0,0 +1,439 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolComputerUse20250124Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolComputerUse20250124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20250124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + DisplayNumber = 0, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + long expectedDisplayHeightPx = 1; + long expectedDisplayWidthPx = 1; + JsonElement expectedName = JsonSerializer.Deserialize("\"computer\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"computer_20250124\""); + List> expectedAllowedCallers = + [ + BetaToolComputerUse20250124AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + long expectedDisplayNumber = 0; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.Equal(expectedDisplayHeightPx, model.DisplayHeightPx); + Assert.Equal(expectedDisplayWidthPx, model.DisplayWidthPx); + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedDisplayNumber, model.DisplayNumber); + Assert.Equal(expectedInputExamples.Count, model.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, model.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(model.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, model.Strict); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolComputerUse20250124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20250124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + DisplayNumber = 0, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolComputerUse20250124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20250124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + DisplayNumber = 0, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedDisplayHeightPx = 1; + long expectedDisplayWidthPx = 1; + JsonElement expectedName = JsonSerializer.Deserialize("\"computer\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"computer_20250124\""); + List> expectedAllowedCallers = + [ + BetaToolComputerUse20250124AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + long expectedDisplayNumber = 0; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.Equal(expectedDisplayHeightPx, deserialized.DisplayHeightPx); + Assert.Equal(expectedDisplayWidthPx, deserialized.DisplayWidthPx); + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedDisplayNumber, deserialized.DisplayNumber); + Assert.Equal(expectedInputExamples.Count, deserialized.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, deserialized.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(deserialized.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, deserialized.Strict); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolComputerUse20250124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20250124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + DisplayNumber = 0, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolComputerUse20250124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + CacheControl = new() { TTL = TTL.TTL5m }, + DisplayNumber = 0, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolComputerUse20250124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + CacheControl = new() { TTL = TTL.TTL5m }, + DisplayNumber = 0, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolComputerUse20250124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + CacheControl = new() { TTL = TTL.TTL5m }, + DisplayNumber = 0, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolComputerUse20250124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + CacheControl = new() { TTL = TTL.TTL5m }, + DisplayNumber = 0, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolComputerUse20250124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20250124AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.DisplayNumber); + Assert.False(model.RawData.ContainsKey("display_number")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolComputerUse20250124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20250124AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaToolComputerUse20250124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20250124AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + DisplayNumber = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.DisplayNumber); + Assert.True(model.RawData.ContainsKey("display_number")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolComputerUse20250124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20250124AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + DisplayNumber = null, + }; + + model.Validate(); + } +} + +public class BetaToolComputerUse20250124AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaToolComputerUse20250124AllowedCaller.Direct)] + [InlineData(BetaToolComputerUse20250124AllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaToolComputerUse20250124AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolComputerUse20250124AllowedCaller.Direct)] + [InlineData(BetaToolComputerUse20250124AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaToolComputerUse20250124AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolComputerUse20251124Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolComputerUse20251124Test.cs new file mode 100644 index 00000000..181f234b --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolComputerUse20251124Test.cs @@ -0,0 +1,457 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolComputerUse20251124Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolComputerUse20251124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20251124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + DisplayNumber = 0, + EnableZoom = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + long expectedDisplayHeightPx = 1; + long expectedDisplayWidthPx = 1; + JsonElement expectedName = JsonSerializer.Deserialize("\"computer\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"computer_20251124\""); + List> expectedAllowedCallers = + [ + BetaToolComputerUse20251124AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + long expectedDisplayNumber = 0; + bool expectedEnableZoom = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.Equal(expectedDisplayHeightPx, model.DisplayHeightPx); + Assert.Equal(expectedDisplayWidthPx, model.DisplayWidthPx); + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedDisplayNumber, model.DisplayNumber); + Assert.Equal(expectedEnableZoom, model.EnableZoom); + Assert.Equal(expectedInputExamples.Count, model.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, model.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(model.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, model.Strict); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolComputerUse20251124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20251124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + DisplayNumber = 0, + EnableZoom = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolComputerUse20251124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20251124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + DisplayNumber = 0, + EnableZoom = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedDisplayHeightPx = 1; + long expectedDisplayWidthPx = 1; + JsonElement expectedName = JsonSerializer.Deserialize("\"computer\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"computer_20251124\""); + List> expectedAllowedCallers = + [ + BetaToolComputerUse20251124AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + long expectedDisplayNumber = 0; + bool expectedEnableZoom = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.Equal(expectedDisplayHeightPx, deserialized.DisplayHeightPx); + Assert.Equal(expectedDisplayWidthPx, deserialized.DisplayWidthPx); + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedDisplayNumber, deserialized.DisplayNumber); + Assert.Equal(expectedEnableZoom, deserialized.EnableZoom); + Assert.Equal(expectedInputExamples.Count, deserialized.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, deserialized.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(deserialized.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, deserialized.Strict); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolComputerUse20251124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20251124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + DisplayNumber = 0, + EnableZoom = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolComputerUse20251124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + CacheControl = new() { TTL = TTL.TTL5m }, + DisplayNumber = 0, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.EnableZoom); + Assert.False(model.RawData.ContainsKey("enable_zoom")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolComputerUse20251124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + CacheControl = new() { TTL = TTL.TTL5m }, + DisplayNumber = 0, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolComputerUse20251124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + CacheControl = new() { TTL = TTL.TTL5m }, + DisplayNumber = 0, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + EnableZoom = null, + InputExamples = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.EnableZoom); + Assert.False(model.RawData.ContainsKey("enable_zoom")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolComputerUse20251124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + CacheControl = new() { TTL = TTL.TTL5m }, + DisplayNumber = 0, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + EnableZoom = null, + InputExamples = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolComputerUse20251124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20251124AllowedCaller.Direct], + DeferLoading = true, + EnableZoom = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.DisplayNumber); + Assert.False(model.RawData.ContainsKey("display_number")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolComputerUse20251124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20251124AllowedCaller.Direct], + DeferLoading = true, + EnableZoom = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaToolComputerUse20251124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20251124AllowedCaller.Direct], + DeferLoading = true, + EnableZoom = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + DisplayNumber = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.DisplayNumber); + Assert.True(model.RawData.ContainsKey("display_number")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolComputerUse20251124 + { + DisplayHeightPx = 1, + DisplayWidthPx = 1, + AllowedCallers = [BetaToolComputerUse20251124AllowedCaller.Direct], + DeferLoading = true, + EnableZoom = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + DisplayNumber = null, + }; + + model.Validate(); + } +} + +public class BetaToolComputerUse20251124AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaToolComputerUse20251124AllowedCaller.Direct)] + [InlineData(BetaToolComputerUse20251124AllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaToolComputerUse20251124AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolComputerUse20251124AllowedCaller.Direct)] + [InlineData(BetaToolComputerUse20251124AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaToolComputerUse20251124AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolReferenceBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolReferenceBlockParamTest.cs new file mode 100644 index 00000000..06fbed46 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolReferenceBlockParamTest.cs @@ -0,0 +1,118 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolReferenceBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolReferenceBlockParam + { + ToolName = "tool_name", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string expectedToolName = "tool_name"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_reference\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedToolName, model.ToolName); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolReferenceBlockParam + { + ToolName = "tool_name", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolReferenceBlockParam + { + ToolName = "tool_name", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedToolName = "tool_name"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_reference\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedToolName, deserialized.ToolName); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolReferenceBlockParam + { + ToolName = "tool_name", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolReferenceBlockParam { ToolName = "tool_name" }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolReferenceBlockParam { ToolName = "tool_name" }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaToolReferenceBlockParam + { + ToolName = "tool_name", + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolReferenceBlockParam + { + ToolName = "tool_name", + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolReferenceBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolReferenceBlockTest.cs new file mode 100644 index 00000000..b21f384a --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolReferenceBlockTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolReferenceBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolReferenceBlock { ToolName = "tool_name" }; + + string expectedToolName = "tool_name"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_reference\""); + + Assert.Equal(expectedToolName, model.ToolName); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolReferenceBlock { ToolName = "tool_name" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolReferenceBlock { ToolName = "tool_name" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedToolName = "tool_name"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_reference\""); + + Assert.Equal(expectedToolName, deserialized.ToolName); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolReferenceBlock { ToolName = "tool_name" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolResultBlockParamTest.cs new file mode 100644 index 00000000..0a2a25f5 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolResultBlockParamTest.cs @@ -0,0 +1,210 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + Content = "string", + IsError = true, + }; + + string expectedToolUseID = "tool_use_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_result\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + BetaToolResultBlockParamContent expectedContent = "string"; + bool expectedIsError = true; + + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedIsError, model.IsError); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + Content = "string", + IsError = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + Content = "string", + IsError = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedToolUseID = "tool_use_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_result\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + BetaToolResultBlockParamContent expectedContent = "string"; + bool expectedIsError = true; + + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedIsError, deserialized.IsError); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + Content = "string", + IsError = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + Assert.Null(model.Content); + Assert.False(model.RawData.ContainsKey("content")); + Assert.Null(model.IsError); + Assert.False(model.RawData.ContainsKey("is_error")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + Content = null, + IsError = null, + }; + + Assert.Null(model.Content); + Assert.False(model.RawData.ContainsKey("content")); + Assert.Null(model.IsError); + Assert.False(model.RawData.ContainsKey("is_error")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + Content = null, + IsError = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolResultBlockParam + { + ToolUseID = "tool_use_id", + Content = "string", + IsError = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolResultBlockParam + { + ToolUseID = "tool_use_id", + Content = "string", + IsError = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaToolResultBlockParam + { + ToolUseID = "tool_use_id", + Content = "string", + IsError = true, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolResultBlockParam + { + ToolUseID = "tool_use_id", + Content = "string", + IsError = true, + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolBm25_20251119Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolBm25_20251119Test.cs new file mode 100644 index 00000000..c0cc36be --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolBm25_20251119Test.cs @@ -0,0 +1,365 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolSearchToolBm25_20251119Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolSearchToolBm25_20251119 + { + Type = BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119, + AllowedCallers = [BetaToolSearchToolBm25_20251119AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"tool_search_tool_bm25\"" + ); + ApiEnum expectedType = + BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119; + List< + ApiEnum + > expectedAllowedCallers = [BetaToolSearchToolBm25_20251119AllowedCaller.Direct]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.Equal(expectedType, model.Type); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedStrict, model.Strict); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolSearchToolBm25_20251119 + { + Type = BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119, + AllowedCallers = [BetaToolSearchToolBm25_20251119AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolSearchToolBm25_20251119 + { + Type = BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119, + AllowedCallers = [BetaToolSearchToolBm25_20251119AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"tool_search_tool_bm25\"" + ); + ApiEnum expectedType = + BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119; + List< + ApiEnum + > expectedAllowedCallers = [BetaToolSearchToolBm25_20251119AllowedCaller.Direct]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.Equal(expectedType, deserialized.Type); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedStrict, deserialized.Strict); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolSearchToolBm25_20251119 + { + Type = BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119, + AllowedCallers = [BetaToolSearchToolBm25_20251119AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolSearchToolBm25_20251119 + { + Type = BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolSearchToolBm25_20251119 + { + Type = BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolSearchToolBm25_20251119 + { + Type = BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119, + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolSearchToolBm25_20251119 + { + Type = BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119, + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolSearchToolBm25_20251119 + { + Type = BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119, + AllowedCallers = [BetaToolSearchToolBm25_20251119AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolSearchToolBm25_20251119 + { + Type = BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119, + AllowedCallers = [BetaToolSearchToolBm25_20251119AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaToolSearchToolBm25_20251119 + { + Type = BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119, + AllowedCallers = [BetaToolSearchToolBm25_20251119AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolSearchToolBm25_20251119 + { + Type = BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119, + AllowedCallers = [BetaToolSearchToolBm25_20251119AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + + CacheControl = null, + }; + + model.Validate(); + } +} + +public class BetaToolSearchToolBm25_20251119TypeTest : TestBase +{ + [Theory] + [InlineData(BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119)] + [InlineData(BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25)] + public void Validation_Works(BetaToolSearchToolBm25_20251119Type rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25_20251119)] + [InlineData(BetaToolSearchToolBm25_20251119Type.ToolSearchToolBm25)] + public void SerializationRoundtrip_Works(BetaToolSearchToolBm25_20251119Type rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} + +public class BetaToolSearchToolBm25_20251119AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaToolSearchToolBm25_20251119AllowedCaller.Direct)] + [InlineData(BetaToolSearchToolBm25_20251119AllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaToolSearchToolBm25_20251119AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolSearchToolBm25_20251119AllowedCaller.Direct)] + [InlineData(BetaToolSearchToolBm25_20251119AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaToolSearchToolBm25_20251119AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolRegex20251119Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolRegex20251119Test.cs new file mode 100644 index 00000000..cfeae276 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolRegex20251119Test.cs @@ -0,0 +1,365 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolSearchToolRegex20251119Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolSearchToolRegex20251119 + { + Type = BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119, + AllowedCallers = [BetaToolSearchToolRegex20251119AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"tool_search_tool_regex\"" + ); + ApiEnum expectedType = + BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119; + List< + ApiEnum + > expectedAllowedCallers = [BetaToolSearchToolRegex20251119AllowedCaller.Direct]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.Equal(expectedType, model.Type); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedStrict, model.Strict); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolSearchToolRegex20251119 + { + Type = BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119, + AllowedCallers = [BetaToolSearchToolRegex20251119AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolSearchToolRegex20251119 + { + Type = BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119, + AllowedCallers = [BetaToolSearchToolRegex20251119AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"tool_search_tool_regex\"" + ); + ApiEnum expectedType = + BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119; + List< + ApiEnum + > expectedAllowedCallers = [BetaToolSearchToolRegex20251119AllowedCaller.Direct]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.Equal(expectedType, deserialized.Type); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedStrict, deserialized.Strict); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolSearchToolRegex20251119 + { + Type = BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119, + AllowedCallers = [BetaToolSearchToolRegex20251119AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolSearchToolRegex20251119 + { + Type = BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolSearchToolRegex20251119 + { + Type = BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolSearchToolRegex20251119 + { + Type = BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119, + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolSearchToolRegex20251119 + { + Type = BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119, + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolSearchToolRegex20251119 + { + Type = BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119, + AllowedCallers = [BetaToolSearchToolRegex20251119AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolSearchToolRegex20251119 + { + Type = BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119, + AllowedCallers = [BetaToolSearchToolRegex20251119AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaToolSearchToolRegex20251119 + { + Type = BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119, + AllowedCallers = [BetaToolSearchToolRegex20251119AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolSearchToolRegex20251119 + { + Type = BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119, + AllowedCallers = [BetaToolSearchToolRegex20251119AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + + CacheControl = null, + }; + + model.Validate(); + } +} + +public class BetaToolSearchToolRegex20251119TypeTest : TestBase +{ + [Theory] + [InlineData(BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119)] + [InlineData(BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex)] + public void Validation_Works(BetaToolSearchToolRegex20251119Type rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex20251119)] + [InlineData(BetaToolSearchToolRegex20251119Type.ToolSearchToolRegex)] + public void SerializationRoundtrip_Works(BetaToolSearchToolRegex20251119Type rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} + +public class BetaToolSearchToolRegex20251119AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaToolSearchToolRegex20251119AllowedCaller.Direct)] + [InlineData(BetaToolSearchToolRegex20251119AllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaToolSearchToolRegex20251119AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolSearchToolRegex20251119AllowedCaller.Direct)] + [InlineData(BetaToolSearchToolRegex20251119AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaToolSearchToolRegex20251119AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolResultBlockParamTest.cs new file mode 100644 index 00000000..007a20e2 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolResultBlockParamTest.cs @@ -0,0 +1,162 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolSearchToolResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolSearchToolResultBlockParam + { + Content = new BetaToolSearchToolResultErrorParam( + BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + BetaToolSearchToolResultBlockParamContent expectedContent = + new BetaToolSearchToolResultErrorParam( + BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"tool_search_tool_result\"" + ); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolSearchToolResultBlockParam + { + Content = new BetaToolSearchToolResultErrorParam( + BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolSearchToolResultBlockParam + { + Content = new BetaToolSearchToolResultErrorParam( + BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaToolSearchToolResultBlockParamContent expectedContent = + new BetaToolSearchToolResultErrorParam( + BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"tool_search_tool_result\"" + ); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolSearchToolResultBlockParam + { + Content = new BetaToolSearchToolResultErrorParam( + BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolSearchToolResultBlockParam + { + Content = new BetaToolSearchToolResultErrorParam( + BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolSearchToolResultBlockParam + { + Content = new BetaToolSearchToolResultErrorParam( + BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaToolSearchToolResultBlockParam + { + Content = new BetaToolSearchToolResultErrorParam( + BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolSearchToolResultBlockParam + { + Content = new BetaToolSearchToolResultErrorParam( + BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolResultBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolResultBlockTest.cs new file mode 100644 index 00000000..370cc62e --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolResultBlockTest.cs @@ -0,0 +1,102 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolSearchToolResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolSearchToolResultBlock + { + Content = new BetaToolSearchToolResultError() + { + ErrorCode = BetaToolSearchToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + BetaToolSearchToolResultBlockContent expectedContent = new BetaToolSearchToolResultError() + { + ErrorCode = BetaToolSearchToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"tool_search_tool_result\"" + ); + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolSearchToolResultBlock + { + Content = new BetaToolSearchToolResultError() + { + ErrorCode = BetaToolSearchToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolSearchToolResultBlock + { + Content = new BetaToolSearchToolResultError() + { + ErrorCode = BetaToolSearchToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaToolSearchToolResultBlockContent expectedContent = new BetaToolSearchToolResultError() + { + ErrorCode = BetaToolSearchToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"tool_search_tool_result\"" + ); + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolSearchToolResultBlock + { + Content = new BetaToolSearchToolResultError() + { + ErrorCode = BetaToolSearchToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }, + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolResultErrorParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolResultErrorParamTest.cs new file mode 100644 index 00000000..075b2df4 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolResultErrorParamTest.cs @@ -0,0 +1,136 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolSearchToolResultErrorParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolSearchToolResultErrorParam + { + ErrorCode = BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput, + }; + + ApiEnum expectedErrorCode = + BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"tool_search_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, model.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolSearchToolResultErrorParam + { + ErrorCode = BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolSearchToolResultErrorParam + { + ErrorCode = BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ApiEnum expectedErrorCode = + BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"tool_search_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, deserialized.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolSearchToolResultErrorParam + { + ErrorCode = BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput, + }; + + model.Validate(); + } +} + +public class BetaToolSearchToolResultErrorParamErrorCodeTest : TestBase +{ + [Theory] + [InlineData(BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput)] + [InlineData(BetaToolSearchToolResultErrorParamErrorCode.Unavailable)] + [InlineData(BetaToolSearchToolResultErrorParamErrorCode.TooManyRequests)] + [InlineData(BetaToolSearchToolResultErrorParamErrorCode.ExecutionTimeExceeded)] + public void Validation_Works(BetaToolSearchToolResultErrorParamErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolSearchToolResultErrorParamErrorCode.InvalidToolInput)] + [InlineData(BetaToolSearchToolResultErrorParamErrorCode.Unavailable)] + [InlineData(BetaToolSearchToolResultErrorParamErrorCode.TooManyRequests)] + [InlineData(BetaToolSearchToolResultErrorParamErrorCode.ExecutionTimeExceeded)] + public void SerializationRoundtrip_Works(BetaToolSearchToolResultErrorParamErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolResultErrorTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolResultErrorTest.cs new file mode 100644 index 00000000..13cab3c2 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolResultErrorTest.cs @@ -0,0 +1,144 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolSearchToolResultErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolSearchToolResultError + { + ErrorCode = BetaToolSearchToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + + ApiEnum expectedErrorCode = + BetaToolSearchToolResultErrorErrorCode.InvalidToolInput; + string expectedErrorMessage = "error_message"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"tool_search_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, model.ErrorCode); + Assert.Equal(expectedErrorMessage, model.ErrorMessage); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolSearchToolResultError + { + ErrorCode = BetaToolSearchToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolSearchToolResultError + { + ErrorCode = BetaToolSearchToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ApiEnum expectedErrorCode = + BetaToolSearchToolResultErrorErrorCode.InvalidToolInput; + string expectedErrorMessage = "error_message"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"tool_search_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, deserialized.ErrorCode); + Assert.Equal(expectedErrorMessage, deserialized.ErrorMessage); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolSearchToolResultError + { + ErrorCode = BetaToolSearchToolResultErrorErrorCode.InvalidToolInput, + ErrorMessage = "error_message", + }; + + model.Validate(); + } +} + +public class BetaToolSearchToolResultErrorErrorCodeTest : TestBase +{ + [Theory] + [InlineData(BetaToolSearchToolResultErrorErrorCode.InvalidToolInput)] + [InlineData(BetaToolSearchToolResultErrorErrorCode.Unavailable)] + [InlineData(BetaToolSearchToolResultErrorErrorCode.TooManyRequests)] + [InlineData(BetaToolSearchToolResultErrorErrorCode.ExecutionTimeExceeded)] + public void Validation_Works(BetaToolSearchToolResultErrorErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolSearchToolResultErrorErrorCode.InvalidToolInput)] + [InlineData(BetaToolSearchToolResultErrorErrorCode.Unavailable)] + [InlineData(BetaToolSearchToolResultErrorErrorCode.TooManyRequests)] + [InlineData(BetaToolSearchToolResultErrorErrorCode.ExecutionTimeExceeded)] + public void SerializationRoundtrip_Works(BetaToolSearchToolResultErrorErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolSearchResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolSearchResultBlockParamTest.cs new file mode 100644 index 00000000..6d56b96c --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolSearchResultBlockParamTest.cs @@ -0,0 +1,125 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolSearchToolSearchResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolSearchToolSearchResultBlockParam + { + ToolReferences = + [ + new() + { + ToolName = "tool_name", + CacheControl = new() { TTL = TTL.TTL5m }, + }, + ], + }; + + List expectedToolReferences = + [ + new() + { + ToolName = "tool_name", + CacheControl = new() { TTL = TTL.TTL5m }, + }, + ]; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"tool_search_tool_search_result\"" + ); + + Assert.Equal(expectedToolReferences.Count, model.ToolReferences.Count); + for (int i = 0; i < expectedToolReferences.Count; i++) + { + Assert.Equal(expectedToolReferences[i], model.ToolReferences[i]); + } + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolSearchToolSearchResultBlockParam + { + ToolReferences = + [ + new() + { + ToolName = "tool_name", + CacheControl = new() { TTL = TTL.TTL5m }, + }, + ], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolSearchToolSearchResultBlockParam + { + ToolReferences = + [ + new() + { + ToolName = "tool_name", + CacheControl = new() { TTL = TTL.TTL5m }, + }, + ], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize( + json + ); + Assert.NotNull(deserialized); + + List expectedToolReferences = + [ + new() + { + ToolName = "tool_name", + CacheControl = new() { TTL = TTL.TTL5m }, + }, + ]; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"tool_search_tool_search_result\"" + ); + + Assert.Equal(expectedToolReferences.Count, deserialized.ToolReferences.Count); + for (int i = 0; i < expectedToolReferences.Count; i++) + { + Assert.Equal(expectedToolReferences[i], deserialized.ToolReferences[i]); + } + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolSearchToolSearchResultBlockParam + { + ToolReferences = + [ + new() + { + ToolName = "tool_name", + CacheControl = new() { TTL = TTL.TTL5m }, + }, + ], + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolSearchResultBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolSearchResultBlockTest.cs new file mode 100644 index 00000000..0b543ac7 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolSearchToolSearchResultBlockTest.cs @@ -0,0 +1,67 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolSearchToolSearchResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolSearchToolSearchResultBlock { ToolReferences = [new("tool_name")] }; + + List expectedToolReferences = [new("tool_name")]; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"tool_search_tool_search_result\"" + ); + + Assert.Equal(expectedToolReferences.Count, model.ToolReferences.Count); + for (int i = 0; i < expectedToolReferences.Count; i++) + { + Assert.Equal(expectedToolReferences[i], model.ToolReferences[i]); + } + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolSearchToolSearchResultBlock { ToolReferences = [new("tool_name")] }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolSearchToolSearchResultBlock { ToolReferences = [new("tool_name")] }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedToolReferences = [new("tool_name")]; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"tool_search_tool_search_result\"" + ); + + Assert.Equal(expectedToolReferences.Count, deserialized.ToolReferences.Count); + for (int i = 0; i < expectedToolReferences.Count; i++) + { + Assert.Equal(expectedToolReferences[i], deserialized.ToolReferences[i]); + } + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolSearchToolSearchResultBlock { ToolReferences = [new("tool_name")] }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolTest.cs new file mode 100644 index 00000000..35af8c8f --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolTest.cs @@ -0,0 +1,765 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaTool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = BetaToolType.Custom, + }; + + InputSchema expectedInputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }; + string expectedName = "name"; + List> expectedAllowedCallers = + [ + BetaToolAllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + string expectedDescription = "Get the current weather in a given location"; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + ApiEnum expectedType = BetaToolType.Custom; + + Assert.Equal(expectedInputSchema, model.InputSchema); + Assert.Equal(expectedName, model.Name); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedDescription, model.Description); + Assert.Equal(expectedInputExamples.Count, model.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, model.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(model.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, model.Strict); + Assert.Equal(expectedType, model.Type); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaTool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = BetaToolType.Custom, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaTool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = BetaToolType.Custom, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + InputSchema expectedInputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }; + string expectedName = "name"; + List> expectedAllowedCallers = + [ + BetaToolAllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + string expectedDescription = "Get the current weather in a given location"; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + ApiEnum expectedType = BetaToolType.Custom; + + Assert.Equal(expectedInputSchema, deserialized.InputSchema); + Assert.Equal(expectedName, deserialized.Name); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedDescription, deserialized.Description); + Assert.Equal(expectedInputExamples.Count, deserialized.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, deserialized.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(deserialized.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, deserialized.Strict); + Assert.Equal(expectedType, deserialized.Type); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaTool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + Type = BetaToolType.Custom, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaTool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = TTL.TTL5m }, + Type = BetaToolType.Custom, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Description); + Assert.False(model.RawData.ContainsKey("description")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaTool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = TTL.TTL5m }, + Type = BetaToolType.Custom, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaTool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = TTL.TTL5m }, + Type = BetaToolType.Custom, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + Description = null, + InputExamples = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Description); + Assert.False(model.RawData.ContainsKey("description")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaTool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = TTL.TTL5m }, + Type = BetaToolType.Custom, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + Description = null, + InputExamples = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaTool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [BetaToolAllowedCaller.Direct], + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Type); + Assert.False(model.RawData.ContainsKey("type")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaTool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [BetaToolAllowedCaller.Direct], + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaTool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [BetaToolAllowedCaller.Direct], + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + Type = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Type); + Assert.True(model.RawData.ContainsKey("type")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaTool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + AllowedCallers = [BetaToolAllowedCaller.Direct], + DeferLoading = true, + Description = "Get the current weather in a given location", + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + Type = null, + }; + + model.Validate(); + } +} + +public class InputSchemaTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new InputSchema + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"object\""); + Dictionary expectedProperties = new() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }; + List expectedRequired = ["location"]; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedProperties.Count, model.Properties.Count); + foreach (var item in expectedProperties) + { + Assert.True(model.Properties.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.Properties[item.Key])); + } + Assert.Equal(expectedRequired.Count, model.Required.Count); + for (int i = 0; i < expectedRequired.Count; i++) + { + Assert.Equal(expectedRequired[i], model.Required[i]); + } + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new InputSchema + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new InputSchema + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"object\""); + Dictionary expectedProperties = new() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }; + List expectedRequired = ["location"]; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedProperties.Count, deserialized.Properties.Count); + foreach (var item in expectedProperties) + { + Assert.True(deserialized.Properties.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.Properties[item.Key])); + } + Assert.Equal(expectedRequired.Count, deserialized.Required.Count); + for (int i = 0; i < expectedRequired.Count; i++) + { + Assert.Equal(expectedRequired[i], deserialized.Required[i]); + } + } + + [Fact] + public void Validation_Works() + { + var model = new InputSchema + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new InputSchema { }; + + Assert.Null(model.Properties); + Assert.False(model.RawData.ContainsKey("properties")); + Assert.Null(model.Required); + Assert.False(model.RawData.ContainsKey("required")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new InputSchema { }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new InputSchema { Properties = null, Required = null }; + + Assert.Null(model.Properties); + Assert.True(model.RawData.ContainsKey("properties")); + Assert.Null(model.Required); + Assert.True(model.RawData.ContainsKey("required")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new InputSchema { Properties = null, Required = null }; + + model.Validate(); + } +} + +public class BetaToolAllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaToolAllowedCaller.Direct)] + [InlineData(BetaToolAllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaToolAllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolAllowedCaller.Direct)] + [InlineData(BetaToolAllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaToolAllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} + +public class BetaToolTypeTest : TestBase +{ + [Theory] + [InlineData(BetaToolType.Custom)] + public void Validation_Works(BetaToolType rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolType.Custom)] + public void SerializationRoundtrip_Works(BetaToolType rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolTextEditor20241022Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolTextEditor20241022Test.cs new file mode 100644 index 00000000..bb6c0212 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolTextEditor20241022Test.cs @@ -0,0 +1,391 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolTextEditor20241022Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolTextEditor20241022 + { + AllowedCallers = [BetaToolTextEditor20241022AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"str_replace_editor\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_20241022\"" + ); + List> expectedAllowedCallers = + [ + BetaToolTextEditor20241022AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedInputExamples.Count, model.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, model.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(model.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, model.Strict); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolTextEditor20241022 + { + AllowedCallers = [BetaToolTextEditor20241022AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolTextEditor20241022 + { + AllowedCallers = [BetaToolTextEditor20241022AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"str_replace_editor\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_20241022\"" + ); + List> expectedAllowedCallers = + [ + BetaToolTextEditor20241022AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedInputExamples.Count, deserialized.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, deserialized.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(deserialized.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, deserialized.Strict); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolTextEditor20241022 + { + AllowedCallers = [BetaToolTextEditor20241022AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolTextEditor20241022 { CacheControl = new() { TTL = TTL.TTL5m } }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolTextEditor20241022 { CacheControl = new() { TTL = TTL.TTL5m } }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolTextEditor20241022 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolTextEditor20241022 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolTextEditor20241022 + { + AllowedCallers = [BetaToolTextEditor20241022AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolTextEditor20241022 + { + AllowedCallers = [BetaToolTextEditor20241022AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaToolTextEditor20241022 + { + AllowedCallers = [BetaToolTextEditor20241022AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolTextEditor20241022 + { + AllowedCallers = [BetaToolTextEditor20241022AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + }; + + model.Validate(); + } +} + +public class BetaToolTextEditor20241022AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaToolTextEditor20241022AllowedCaller.Direct)] + [InlineData(BetaToolTextEditor20241022AllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaToolTextEditor20241022AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolTextEditor20241022AllowedCaller.Direct)] + [InlineData(BetaToolTextEditor20241022AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaToolTextEditor20241022AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolTextEditor20250124Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolTextEditor20250124Test.cs new file mode 100644 index 00000000..ec1bd2b2 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolTextEditor20250124Test.cs @@ -0,0 +1,391 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolTextEditor20250124Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolTextEditor20250124 + { + AllowedCallers = [BetaToolTextEditor20250124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"str_replace_editor\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_20250124\"" + ); + List> expectedAllowedCallers = + [ + BetaToolTextEditor20250124AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedInputExamples.Count, model.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, model.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(model.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, model.Strict); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolTextEditor20250124 + { + AllowedCallers = [BetaToolTextEditor20250124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolTextEditor20250124 + { + AllowedCallers = [BetaToolTextEditor20250124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"str_replace_editor\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_20250124\"" + ); + List> expectedAllowedCallers = + [ + BetaToolTextEditor20250124AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedInputExamples.Count, deserialized.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, deserialized.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(deserialized.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, deserialized.Strict); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolTextEditor20250124 + { + AllowedCallers = [BetaToolTextEditor20250124AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolTextEditor20250124 { CacheControl = new() { TTL = TTL.TTL5m } }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolTextEditor20250124 { CacheControl = new() { TTL = TTL.TTL5m } }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolTextEditor20250124 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolTextEditor20250124 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolTextEditor20250124 + { + AllowedCallers = [BetaToolTextEditor20250124AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolTextEditor20250124 + { + AllowedCallers = [BetaToolTextEditor20250124AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaToolTextEditor20250124 + { + AllowedCallers = [BetaToolTextEditor20250124AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolTextEditor20250124 + { + AllowedCallers = [BetaToolTextEditor20250124AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + }; + + model.Validate(); + } +} + +public class BetaToolTextEditor20250124AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaToolTextEditor20250124AllowedCaller.Direct)] + [InlineData(BetaToolTextEditor20250124AllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaToolTextEditor20250124AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolTextEditor20250124AllowedCaller.Direct)] + [InlineData(BetaToolTextEditor20250124AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaToolTextEditor20250124AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolTextEditor20250429Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolTextEditor20250429Test.cs new file mode 100644 index 00000000..4935a60b --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolTextEditor20250429Test.cs @@ -0,0 +1,391 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolTextEditor20250429Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolTextEditor20250429 + { + AllowedCallers = [BetaToolTextEditor20250429AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"str_replace_based_edit_tool\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_20250429\"" + ); + List> expectedAllowedCallers = + [ + BetaToolTextEditor20250429AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedInputExamples.Count, model.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, model.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(model.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, model.Strict); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolTextEditor20250429 + { + AllowedCallers = [BetaToolTextEditor20250429AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolTextEditor20250429 + { + AllowedCallers = [BetaToolTextEditor20250429AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"str_replace_based_edit_tool\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_20250429\"" + ); + List> expectedAllowedCallers = + [ + BetaToolTextEditor20250429AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedInputExamples.Count, deserialized.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, deserialized.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(deserialized.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedStrict, deserialized.Strict); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolTextEditor20250429 + { + AllowedCallers = [BetaToolTextEditor20250429AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolTextEditor20250429 { CacheControl = new() { TTL = TTL.TTL5m } }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolTextEditor20250429 { CacheControl = new() { TTL = TTL.TTL5m } }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolTextEditor20250429 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolTextEditor20250429 + { + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolTextEditor20250429 + { + AllowedCallers = [BetaToolTextEditor20250429AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolTextEditor20250429 + { + AllowedCallers = [BetaToolTextEditor20250429AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaToolTextEditor20250429 + { + AllowedCallers = [BetaToolTextEditor20250429AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolTextEditor20250429 + { + AllowedCallers = [BetaToolTextEditor20250429AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + }; + + model.Validate(); + } +} + +public class BetaToolTextEditor20250429AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaToolTextEditor20250429AllowedCaller.Direct)] + [InlineData(BetaToolTextEditor20250429AllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaToolTextEditor20250429AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolTextEditor20250429AllowedCaller.Direct)] + [InlineData(BetaToolTextEditor20250429AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaToolTextEditor20250429AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolTextEditor20250728Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolTextEditor20250728Test.cs new file mode 100644 index 00000000..539441f8 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolTextEditor20250728Test.cs @@ -0,0 +1,415 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolTextEditor20250728Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolTextEditor20250728 + { + AllowedCallers = [BetaToolTextEditor20250728AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + MaxCharacters = 1, + Strict = true, + }; + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"str_replace_based_edit_tool\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_20250728\"" + ); + List> expectedAllowedCallers = + [ + BetaToolTextEditor20250728AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + long expectedMaxCharacters = 1; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedInputExamples.Count, model.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, model.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(model.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedMaxCharacters, model.MaxCharacters); + Assert.Equal(expectedStrict, model.Strict); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolTextEditor20250728 + { + AllowedCallers = [BetaToolTextEditor20250728AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + MaxCharacters = 1, + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolTextEditor20250728 + { + AllowedCallers = [BetaToolTextEditor20250728AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + MaxCharacters = 1, + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"str_replace_based_edit_tool\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_20250728\"" + ); + List> expectedAllowedCallers = + [ + BetaToolTextEditor20250728AllowedCaller.Direct, + ]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + List> expectedInputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ]; + long expectedMaxCharacters = 1; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedInputExamples.Count, deserialized.InputExamples.Count); + for (int i = 0; i < expectedInputExamples.Count; i++) + { + Assert.Equal(expectedInputExamples[i].Count, deserialized.InputExamples[i].Count); + foreach (var item in expectedInputExamples[i]) + { + Assert.True(deserialized.InputExamples[i].TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.InputExamples[i][item.Key])); + } + } + Assert.Equal(expectedMaxCharacters, deserialized.MaxCharacters); + Assert.Equal(expectedStrict, deserialized.Strict); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolTextEditor20250728 + { + AllowedCallers = [BetaToolTextEditor20250728AllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + MaxCharacters = 1, + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolTextEditor20250728 + { + CacheControl = new() { TTL = TTL.TTL5m }, + MaxCharacters = 1, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolTextEditor20250728 + { + CacheControl = new() { TTL = TTL.TTL5m }, + MaxCharacters = 1, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolTextEditor20250728 + { + CacheControl = new() { TTL = TTL.TTL5m }, + MaxCharacters = 1, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.InputExamples); + Assert.False(model.RawData.ContainsKey("input_examples")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolTextEditor20250728 + { + CacheControl = new() { TTL = TTL.TTL5m }, + MaxCharacters = 1, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + InputExamples = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolTextEditor20250728 + { + AllowedCallers = [BetaToolTextEditor20250728AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.MaxCharacters); + Assert.False(model.RawData.ContainsKey("max_characters")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolTextEditor20250728 + { + AllowedCallers = [BetaToolTextEditor20250728AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaToolTextEditor20250728 + { + AllowedCallers = [BetaToolTextEditor20250728AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + MaxCharacters = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.MaxCharacters); + Assert.True(model.RawData.ContainsKey("max_characters")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolTextEditor20250728 + { + AllowedCallers = [BetaToolTextEditor20250728AllowedCaller.Direct], + DeferLoading = true, + InputExamples = + [ + new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + ], + Strict = true, + + CacheControl = null, + MaxCharacters = null, + }; + + model.Validate(); + } +} + +public class BetaToolTextEditor20250728AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaToolTextEditor20250728AllowedCaller.Direct)] + [InlineData(BetaToolTextEditor20250728AllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaToolTextEditor20250728AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaToolTextEditor20250728AllowedCaller.Direct)] + [InlineData(BetaToolTextEditor20250728AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaToolTextEditor20250728AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolUnionTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolUnionTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolUnionTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolUseBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolUseBlockParamTest.cs new file mode 100644 index 00000000..20479a41 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolUseBlockParamTest.cs @@ -0,0 +1,279 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolUseBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Caller = new BetaDirectCaller(), + }; + + string expectedID = "id"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + string expectedName = "x"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_use\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + BetaToolUseBlockParamCaller expectedCaller = new BetaDirectCaller(); + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedInput.Count, model.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(model.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.Input[item.Key])); + } + Assert.Equal(expectedName, model.Name); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedCaller, model.Caller); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Caller = new BetaDirectCaller(), + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Caller = new BetaDirectCaller(), + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "id"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + string expectedName = "x"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_use\""); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + BetaToolUseBlockParamCaller expectedCaller = new BetaDirectCaller(); + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedInput.Count, deserialized.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(deserialized.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.Input[item.Key])); + } + Assert.Equal(expectedName, deserialized.Name); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedCaller, deserialized.Caller); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Caller = new BetaDirectCaller(), + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + Assert.Null(model.Caller); + Assert.False(model.RawData.ContainsKey("caller")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + Caller = null, + }; + + Assert.Null(model.Caller); + Assert.False(model.RawData.ContainsKey("caller")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + Caller = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + Caller = new BetaDirectCaller(), + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + Caller = new BetaDirectCaller(), + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + Caller = new BetaDirectCaller(), + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + Caller = new BetaDirectCaller(), + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolUseBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolUseBlockTest.cs new file mode 100644 index 00000000..e3059d6c --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolUseBlockTest.cs @@ -0,0 +1,193 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolUseBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + Caller = new BetaDirectCaller(), + }; + + string expectedID = "id"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + string expectedName = "x"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_use\""); + BetaToolUseBlockCaller expectedCaller = new BetaDirectCaller(); + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedInput.Count, model.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(model.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.Input[item.Key])); + } + Assert.Equal(expectedName, model.Name); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCaller, model.Caller); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + Caller = new BetaDirectCaller(), + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + Caller = new BetaDirectCaller(), + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "id"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + string expectedName = "x"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_use\""); + BetaToolUseBlockCaller expectedCaller = new BetaDirectCaller(); + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedInput.Count, deserialized.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(deserialized.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.Input[item.Key])); + } + Assert.Equal(expectedName, deserialized.Name); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCaller, deserialized.Caller); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + Caller = new BetaDirectCaller(), + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + }; + + Assert.Null(model.Caller); + Assert.False(model.RawData.ContainsKey("caller")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + + // Null should be interpreted as omitted for these properties + Caller = null, + }; + + Assert.Null(model.Caller); + Assert.False(model.RawData.ContainsKey("caller")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + + // Null should be interpreted as omitted for these properties + Caller = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolUsesKeepTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolUsesKeepTest.cs new file mode 100644 index 00000000..4099c182 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolUsesKeepTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolUsesKeepTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolUsesKeep { Value = 0 }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_uses\""); + long expectedValue = 0; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedValue, model.Value); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolUsesKeep { Value = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolUsesKeep { Value = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_uses\""); + long expectedValue = 0; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedValue, deserialized.Value); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolUsesKeep { Value = 0 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaToolUsesTriggerTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolUsesTriggerTest.cs new file mode 100644 index 00000000..128881fe --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaToolUsesTriggerTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaToolUsesTriggerTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaToolUsesTrigger { Value = 1 }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_uses\""); + long expectedValue = 1; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedValue, model.Value); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaToolUsesTrigger { Value = 1 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaToolUsesTrigger { Value = 1 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_uses\""); + long expectedValue = 1; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedValue, deserialized.Value); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaToolUsesTrigger { Value = 1 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaURLImageSourceTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaURLImageSourceTest.cs new file mode 100644 index 00000000..45660c78 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaURLImageSourceTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaURLImageSourceTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaURLImageSource { URL = "url" }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"url\""); + string expectedURL = "url"; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedURL, model.URL); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaURLImageSource { URL = "url" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaURLImageSource { URL = "url" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"url\""); + string expectedURL = "url"; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedURL, deserialized.URL); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaURLImageSource { URL = "url" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaURLPDFSourceTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaURLPDFSourceTest.cs new file mode 100644 index 00000000..dd34296b --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaURLPDFSourceTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaURLPDFSourceTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaURLPDFSource { URL = "url" }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"url\""); + string expectedURL = "url"; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedURL, model.URL); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaURLPDFSource { URL = "url" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaURLPDFSource { URL = "url" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"url\""); + string expectedURL = "url"; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedURL, deserialized.URL); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaURLPDFSource { URL = "url" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaUsageTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaUsageTest.cs new file mode 100644 index 00000000..ba98fff4 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaUsageTest.cs @@ -0,0 +1,186 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaUsageTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaUsage + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = BetaUsageServiceTier.Standard, + }; + + BetaCacheCreation expectedCacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }; + long expectedCacheCreationInputTokens = 2051; + long expectedCacheReadInputTokens = 2051; + long expectedInputTokens = 2095; + long expectedOutputTokens = 503; + BetaServerToolUsage expectedServerToolUse = new() + { + WebFetchRequests = 2, + WebSearchRequests = 0, + }; + ApiEnum expectedServiceTier = BetaUsageServiceTier.Standard; + + Assert.Equal(expectedCacheCreation, model.CacheCreation); + Assert.Equal(expectedCacheCreationInputTokens, model.CacheCreationInputTokens); + Assert.Equal(expectedCacheReadInputTokens, model.CacheReadInputTokens); + Assert.Equal(expectedInputTokens, model.InputTokens); + Assert.Equal(expectedOutputTokens, model.OutputTokens); + Assert.Equal(expectedServerToolUse, model.ServerToolUse); + Assert.Equal(expectedServiceTier, model.ServiceTier); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaUsage + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = BetaUsageServiceTier.Standard, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaUsage + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = BetaUsageServiceTier.Standard, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaCacheCreation expectedCacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }; + long expectedCacheCreationInputTokens = 2051; + long expectedCacheReadInputTokens = 2051; + long expectedInputTokens = 2095; + long expectedOutputTokens = 503; + BetaServerToolUsage expectedServerToolUse = new() + { + WebFetchRequests = 2, + WebSearchRequests = 0, + }; + ApiEnum expectedServiceTier = BetaUsageServiceTier.Standard; + + Assert.Equal(expectedCacheCreation, deserialized.CacheCreation); + Assert.Equal(expectedCacheCreationInputTokens, deserialized.CacheCreationInputTokens); + Assert.Equal(expectedCacheReadInputTokens, deserialized.CacheReadInputTokens); + Assert.Equal(expectedInputTokens, deserialized.InputTokens); + Assert.Equal(expectedOutputTokens, deserialized.OutputTokens); + Assert.Equal(expectedServerToolUse, deserialized.ServerToolUse); + Assert.Equal(expectedServiceTier, deserialized.ServiceTier); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaUsage + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new() { WebFetchRequests = 2, WebSearchRequests = 0 }, + ServiceTier = BetaUsageServiceTier.Standard, + }; + + model.Validate(); + } +} + +public class BetaUsageServiceTierTest : TestBase +{ + [Theory] + [InlineData(BetaUsageServiceTier.Standard)] + [InlineData(BetaUsageServiceTier.Priority)] + [InlineData(BetaUsageServiceTier.Batch)] + public void Validation_Works(BetaUsageServiceTier rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaUsageServiceTier.Standard)] + [InlineData(BetaUsageServiceTier.Priority)] + [InlineData(BetaUsageServiceTier.Batch)] + public void SerializationRoundtrip_Works(BetaUsageServiceTier rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchBlockParamTest.cs new file mode 100644 index 00000000..89f086d5 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchBlockParamTest.cs @@ -0,0 +1,206 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebFetchBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaWebFetchBlockParam + { + Content = new() + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }, + URL = "url", + RetrievedAt = "retrieved_at", + }; + + BetaRequestDocumentBlock expectedContent = new() + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"web_fetch_result\""); + string expectedURL = "url"; + string expectedRetrievedAt = "retrieved_at"; + + Assert.Equal(expectedContent, model.Content); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedURL, model.URL); + Assert.Equal(expectedRetrievedAt, model.RetrievedAt); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaWebFetchBlockParam + { + Content = new() + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }, + URL = "url", + RetrievedAt = "retrieved_at", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaWebFetchBlockParam + { + Content = new() + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }, + URL = "url", + RetrievedAt = "retrieved_at", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaRequestDocumentBlock expectedContent = new() + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"web_fetch_result\""); + string expectedURL = "url"; + string expectedRetrievedAt = "retrieved_at"; + + Assert.Equal(expectedContent, deserialized.Content); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedURL, deserialized.URL); + Assert.Equal(expectedRetrievedAt, deserialized.RetrievedAt); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaWebFetchBlockParam + { + Content = new() + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }, + URL = "url", + RetrievedAt = "retrieved_at", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaWebFetchBlockParam + { + Content = new() + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }, + URL = "url", + }; + + Assert.Null(model.RetrievedAt); + Assert.False(model.RawData.ContainsKey("retrieved_at")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaWebFetchBlockParam + { + Content = new() + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }, + URL = "url", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaWebFetchBlockParam + { + Content = new() + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }, + URL = "url", + + RetrievedAt = null, + }; + + Assert.Null(model.RetrievedAt); + Assert.True(model.RawData.ContainsKey("retrieved_at")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaWebFetchBlockParam + { + Content = new() + { + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }, + URL = "url", + + RetrievedAt = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchBlockTest.cs new file mode 100644 index 00000000..82fc98d3 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchBlockTest.cs @@ -0,0 +1,112 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebFetchBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaWebFetchBlock + { + Content = new() + { + Citations = new(true), + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + Title = "title", + }, + RetrievedAt = "retrieved_at", + URL = "url", + }; + + BetaDocumentBlock expectedContent = new() + { + Citations = new(true), + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + Title = "title", + }; + string expectedRetrievedAt = "retrieved_at"; + JsonElement expectedType = JsonSerializer.Deserialize("\"web_fetch_result\""); + string expectedURL = "url"; + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedRetrievedAt, model.RetrievedAt); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedURL, model.URL); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaWebFetchBlock + { + Content = new() + { + Citations = new(true), + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + Title = "title", + }, + RetrievedAt = "retrieved_at", + URL = "url", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaWebFetchBlock + { + Content = new() + { + Citations = new(true), + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + Title = "title", + }, + RetrievedAt = "retrieved_at", + URL = "url", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaDocumentBlock expectedContent = new() + { + Citations = new(true), + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + Title = "title", + }; + string expectedRetrievedAt = "retrieved_at"; + JsonElement expectedType = JsonSerializer.Deserialize("\"web_fetch_result\""); + string expectedURL = "url"; + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedRetrievedAt, deserialized.RetrievedAt); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedURL, deserialized.URL); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaWebFetchBlock + { + Content = new() + { + Citations = new(true), + Source = new BetaBase64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + Title = "title", + }, + RetrievedAt = "retrieved_at", + URL = "url", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchTool20250910Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchTool20250910Test.cs new file mode 100644 index 00000000..87fe98a1 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchTool20250910Test.cs @@ -0,0 +1,401 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebFetchTool20250910Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaWebFetchTool20250910 + { + AllowedCallers = [BetaWebFetchTool20250910AllowedCaller.Direct], + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + DeferLoading = true, + MaxContentTokens = 1, + MaxUses = 1, + Strict = true, + }; + + JsonElement expectedName = JsonSerializer.Deserialize("\"web_fetch\""); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_fetch_20250910\"" + ); + List> expectedAllowedCallers = + [ + BetaWebFetchTool20250910AllowedCaller.Direct, + ]; + List expectedAllowedDomains = ["string"]; + List expectedBlockedDomains = ["string"]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + BetaCitationsConfigParam expectedCitations = new() { Enabled = true }; + bool expectedDeferLoading = true; + long expectedMaxContentTokens = 1; + long expectedMaxUses = 1; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedAllowedDomains.Count, model.AllowedDomains.Count); + for (int i = 0; i < expectedAllowedDomains.Count; i++) + { + Assert.Equal(expectedAllowedDomains[i], model.AllowedDomains[i]); + } + Assert.Equal(expectedBlockedDomains.Count, model.BlockedDomains.Count); + for (int i = 0; i < expectedBlockedDomains.Count; i++) + { + Assert.Equal(expectedBlockedDomains[i], model.BlockedDomains[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedCitations, model.Citations); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedMaxContentTokens, model.MaxContentTokens); + Assert.Equal(expectedMaxUses, model.MaxUses); + Assert.Equal(expectedStrict, model.Strict); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaWebFetchTool20250910 + { + AllowedCallers = [BetaWebFetchTool20250910AllowedCaller.Direct], + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + DeferLoading = true, + MaxContentTokens = 1, + MaxUses = 1, + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaWebFetchTool20250910 + { + AllowedCallers = [BetaWebFetchTool20250910AllowedCaller.Direct], + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + DeferLoading = true, + MaxContentTokens = 1, + MaxUses = 1, + Strict = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize("\"web_fetch\""); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_fetch_20250910\"" + ); + List> expectedAllowedCallers = + [ + BetaWebFetchTool20250910AllowedCaller.Direct, + ]; + List expectedAllowedDomains = ["string"]; + List expectedBlockedDomains = ["string"]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + BetaCitationsConfigParam expectedCitations = new() { Enabled = true }; + bool expectedDeferLoading = true; + long expectedMaxContentTokens = 1; + long expectedMaxUses = 1; + bool expectedStrict = true; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedAllowedDomains.Count, deserialized.AllowedDomains.Count); + for (int i = 0; i < expectedAllowedDomains.Count; i++) + { + Assert.Equal(expectedAllowedDomains[i], deserialized.AllowedDomains[i]); + } + Assert.Equal(expectedBlockedDomains.Count, deserialized.BlockedDomains.Count); + for (int i = 0; i < expectedBlockedDomains.Count; i++) + { + Assert.Equal(expectedBlockedDomains[i], deserialized.BlockedDomains[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedCitations, deserialized.Citations); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedMaxContentTokens, deserialized.MaxContentTokens); + Assert.Equal(expectedMaxUses, deserialized.MaxUses); + Assert.Equal(expectedStrict, deserialized.Strict); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaWebFetchTool20250910 + { + AllowedCallers = [BetaWebFetchTool20250910AllowedCaller.Direct], + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + DeferLoading = true, + MaxContentTokens = 1, + MaxUses = 1, + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaWebFetchTool20250910 + { + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + MaxContentTokens = 1, + MaxUses = 1, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaWebFetchTool20250910 + { + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + MaxContentTokens = 1, + MaxUses = 1, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaWebFetchTool20250910 + { + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + MaxContentTokens = 1, + MaxUses = 1, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaWebFetchTool20250910 + { + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + MaxContentTokens = 1, + MaxUses = 1, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaWebFetchTool20250910 + { + AllowedCallers = [BetaWebFetchTool20250910AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + }; + + Assert.Null(model.AllowedDomains); + Assert.False(model.RawData.ContainsKey("allowed_domains")); + Assert.Null(model.BlockedDomains); + Assert.False(model.RawData.ContainsKey("blocked_domains")); + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Citations); + Assert.False(model.RawData.ContainsKey("citations")); + Assert.Null(model.MaxContentTokens); + Assert.False(model.RawData.ContainsKey("max_content_tokens")); + Assert.Null(model.MaxUses); + Assert.False(model.RawData.ContainsKey("max_uses")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaWebFetchTool20250910 + { + AllowedCallers = [BetaWebFetchTool20250910AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaWebFetchTool20250910 + { + AllowedCallers = [BetaWebFetchTool20250910AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + + AllowedDomains = null, + BlockedDomains = null, + CacheControl = null, + Citations = null, + MaxContentTokens = null, + MaxUses = null, + }; + + Assert.Null(model.AllowedDomains); + Assert.True(model.RawData.ContainsKey("allowed_domains")); + Assert.Null(model.BlockedDomains); + Assert.True(model.RawData.ContainsKey("blocked_domains")); + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Citations); + Assert.True(model.RawData.ContainsKey("citations")); + Assert.Null(model.MaxContentTokens); + Assert.True(model.RawData.ContainsKey("max_content_tokens")); + Assert.Null(model.MaxUses); + Assert.True(model.RawData.ContainsKey("max_uses")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaWebFetchTool20250910 + { + AllowedCallers = [BetaWebFetchTool20250910AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + + AllowedDomains = null, + BlockedDomains = null, + CacheControl = null, + Citations = null, + MaxContentTokens = null, + MaxUses = null, + }; + + model.Validate(); + } +} + +public class BetaWebFetchTool20250910AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaWebFetchTool20250910AllowedCaller.Direct)] + [InlineData(BetaWebFetchTool20250910AllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaWebFetchTool20250910AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaWebFetchTool20250910AllowedCaller.Direct)] + [InlineData(BetaWebFetchTool20250910AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaWebFetchTool20250910AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchToolResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchToolResultBlockParamTest.cs new file mode 100644 index 00000000..a678fabe --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchToolResultBlockParamTest.cs @@ -0,0 +1,162 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebFetchToolResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaWebFetchToolResultBlockParam + { + Content = new BetaWebFetchToolResultErrorBlockParam( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + BetaWebFetchToolResultBlockParamContent expectedContent = + new BetaWebFetchToolResultErrorBlockParam( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_fetch_tool_result\"" + ); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaWebFetchToolResultBlockParam + { + Content = new BetaWebFetchToolResultErrorBlockParam( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaWebFetchToolResultBlockParam + { + Content = new BetaWebFetchToolResultErrorBlockParam( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaWebFetchToolResultBlockParamContent expectedContent = + new BetaWebFetchToolResultErrorBlockParam( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_fetch_tool_result\"" + ); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaWebFetchToolResultBlockParam + { + Content = new BetaWebFetchToolResultErrorBlockParam( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaWebFetchToolResultBlockParam + { + Content = new BetaWebFetchToolResultErrorBlockParam( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaWebFetchToolResultBlockParam + { + Content = new BetaWebFetchToolResultErrorBlockParam( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaWebFetchToolResultBlockParam + { + Content = new BetaWebFetchToolResultErrorBlockParam( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaWebFetchToolResultBlockParam + { + Content = new BetaWebFetchToolResultErrorBlockParam( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchToolResultBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchToolResultBlockTest.cs new file mode 100644 index 00000000..2cc3a6c0 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchToolResultBlockTest.cs @@ -0,0 +1,90 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebFetchToolResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaWebFetchToolResultBlock + { + Content = new BetaWebFetchToolResultErrorBlock( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + BetaWebFetchToolResultBlockContent expectedContent = new BetaWebFetchToolResultErrorBlock( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_fetch_tool_result\"" + ); + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaWebFetchToolResultBlock + { + Content = new BetaWebFetchToolResultErrorBlock( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaWebFetchToolResultBlock + { + Content = new BetaWebFetchToolResultErrorBlock( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaWebFetchToolResultBlockContent expectedContent = new BetaWebFetchToolResultErrorBlock( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_fetch_tool_result\"" + ); + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaWebFetchToolResultBlock + { + Content = new BetaWebFetchToolResultErrorBlock( + BetaWebFetchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchToolResultErrorBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchToolResultErrorBlockParamTest.cs new file mode 100644 index 00000000..75197560 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchToolResultErrorBlockParamTest.cs @@ -0,0 +1,73 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebFetchToolResultErrorBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaWebFetchToolResultErrorBlockParam + { + ErrorCode = BetaWebFetchToolResultErrorCode.InvalidToolInput, + }; + + ApiEnum expectedErrorCode = + BetaWebFetchToolResultErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_fetch_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, model.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaWebFetchToolResultErrorBlockParam + { + ErrorCode = BetaWebFetchToolResultErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaWebFetchToolResultErrorBlockParam + { + ErrorCode = BetaWebFetchToolResultErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ApiEnum expectedErrorCode = + BetaWebFetchToolResultErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_fetch_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, deserialized.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaWebFetchToolResultErrorBlockParam + { + ErrorCode = BetaWebFetchToolResultErrorCode.InvalidToolInput, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchToolResultErrorBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchToolResultErrorBlockTest.cs new file mode 100644 index 00000000..c111ec7d --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchToolResultErrorBlockTest.cs @@ -0,0 +1,73 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebFetchToolResultErrorBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaWebFetchToolResultErrorBlock + { + ErrorCode = BetaWebFetchToolResultErrorCode.InvalidToolInput, + }; + + ApiEnum expectedErrorCode = + BetaWebFetchToolResultErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_fetch_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, model.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaWebFetchToolResultErrorBlock + { + ErrorCode = BetaWebFetchToolResultErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaWebFetchToolResultErrorBlock + { + ErrorCode = BetaWebFetchToolResultErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ApiEnum expectedErrorCode = + BetaWebFetchToolResultErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_fetch_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, deserialized.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaWebFetchToolResultErrorBlock + { + ErrorCode = BetaWebFetchToolResultErrorCode.InvalidToolInput, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchToolResultErrorCodeTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchToolResultErrorCodeTest.cs new file mode 100644 index 00000000..932e61e4 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebFetchToolResultErrorCodeTest.cs @@ -0,0 +1,72 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebFetchToolResultErrorCodeTest : TestBase +{ + [Theory] + [InlineData(BetaWebFetchToolResultErrorCode.InvalidToolInput)] + [InlineData(BetaWebFetchToolResultErrorCode.URLTooLong)] + [InlineData(BetaWebFetchToolResultErrorCode.URLNotAllowed)] + [InlineData(BetaWebFetchToolResultErrorCode.URLNotAccessible)] + [InlineData(BetaWebFetchToolResultErrorCode.UnsupportedContentType)] + [InlineData(BetaWebFetchToolResultErrorCode.TooManyRequests)] + [InlineData(BetaWebFetchToolResultErrorCode.MaxUsesExceeded)] + [InlineData(BetaWebFetchToolResultErrorCode.Unavailable)] + public void Validation_Works(BetaWebFetchToolResultErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaWebFetchToolResultErrorCode.InvalidToolInput)] + [InlineData(BetaWebFetchToolResultErrorCode.URLTooLong)] + [InlineData(BetaWebFetchToolResultErrorCode.URLNotAllowed)] + [InlineData(BetaWebFetchToolResultErrorCode.URLNotAccessible)] + [InlineData(BetaWebFetchToolResultErrorCode.UnsupportedContentType)] + [InlineData(BetaWebFetchToolResultErrorCode.TooManyRequests)] + [InlineData(BetaWebFetchToolResultErrorCode.MaxUsesExceeded)] + [InlineData(BetaWebFetchToolResultErrorCode.Unavailable)] + public void SerializationRoundtrip_Works(BetaWebFetchToolResultErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchResultBlockParamTest.cs new file mode 100644 index 00000000..4d0e821f --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchResultBlockParamTest.cs @@ -0,0 +1,148 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebSearchResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaWebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }; + + string expectedEncryptedContent = "encrypted_content"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize("\"web_search_result\""); + string expectedURL = "url"; + string expectedPageAge = "page_age"; + + Assert.Equal(expectedEncryptedContent, model.EncryptedContent); + Assert.Equal(expectedTitle, model.Title); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedURL, model.URL); + Assert.Equal(expectedPageAge, model.PageAge); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaWebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaWebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedEncryptedContent = "encrypted_content"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize("\"web_search_result\""); + string expectedURL = "url"; + string expectedPageAge = "page_age"; + + Assert.Equal(expectedEncryptedContent, deserialized.EncryptedContent); + Assert.Equal(expectedTitle, deserialized.Title); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedURL, deserialized.URL); + Assert.Equal(expectedPageAge, deserialized.PageAge); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaWebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaWebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + }; + + Assert.Null(model.PageAge); + Assert.False(model.RawData.ContainsKey("page_age")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaWebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaWebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + + PageAge = null, + }; + + Assert.Null(model.PageAge); + Assert.True(model.RawData.ContainsKey("page_age")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaWebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + + PageAge = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchResultBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchResultBlockTest.cs new file mode 100644 index 00000000..01b35441 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchResultBlockTest.cs @@ -0,0 +1,90 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebSearchResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaWebSearchResultBlock + { + EncryptedContent = "encrypted_content", + PageAge = "page_age", + Title = "title", + URL = "url", + }; + + string expectedEncryptedContent = "encrypted_content"; + string expectedPageAge = "page_age"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize("\"web_search_result\""); + string expectedURL = "url"; + + Assert.Equal(expectedEncryptedContent, model.EncryptedContent); + Assert.Equal(expectedPageAge, model.PageAge); + Assert.Equal(expectedTitle, model.Title); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedURL, model.URL); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaWebSearchResultBlock + { + EncryptedContent = "encrypted_content", + PageAge = "page_age", + Title = "title", + URL = "url", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaWebSearchResultBlock + { + EncryptedContent = "encrypted_content", + PageAge = "page_age", + Title = "title", + URL = "url", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedEncryptedContent = "encrypted_content"; + string expectedPageAge = "page_age"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize("\"web_search_result\""); + string expectedURL = "url"; + + Assert.Equal(expectedEncryptedContent, deserialized.EncryptedContent); + Assert.Equal(expectedPageAge, deserialized.PageAge); + Assert.Equal(expectedTitle, deserialized.Title); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedURL, deserialized.URL); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaWebSearchResultBlock + { + EncryptedContent = "encrypted_content", + PageAge = "page_age", + Title = "title", + URL = "url", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchTool20250305Test.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchTool20250305Test.cs new file mode 100644 index 00000000..b2e824e1 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchTool20250305Test.cs @@ -0,0 +1,587 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebSearchTool20250305Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaWebSearchTool20250305 + { + AllowedCallers = [BetaWebSearchTool20250305AllowedCaller.Direct], + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + MaxUses = 1, + Strict = true, + UserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }, + }; + + JsonElement expectedName = JsonSerializer.Deserialize("\"web_search\""); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_20250305\"" + ); + List> expectedAllowedCallers = + [ + BetaWebSearchTool20250305AllowedCaller.Direct, + ]; + List expectedAllowedDomains = ["string"]; + List expectedBlockedDomains = ["string"]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + long expectedMaxUses = 1; + bool expectedStrict = true; + UserLocation expectedUserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedAllowedCallers.Count, model.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], model.AllowedCallers[i]); + } + Assert.Equal(expectedAllowedDomains.Count, model.AllowedDomains.Count); + for (int i = 0; i < expectedAllowedDomains.Count; i++) + { + Assert.Equal(expectedAllowedDomains[i], model.AllowedDomains[i]); + } + Assert.Equal(expectedBlockedDomains.Count, model.BlockedDomains.Count); + for (int i = 0; i < expectedBlockedDomains.Count; i++) + { + Assert.Equal(expectedBlockedDomains[i], model.BlockedDomains[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDeferLoading, model.DeferLoading); + Assert.Equal(expectedMaxUses, model.MaxUses); + Assert.Equal(expectedStrict, model.Strict); + Assert.Equal(expectedUserLocation, model.UserLocation); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaWebSearchTool20250305 + { + AllowedCallers = [BetaWebSearchTool20250305AllowedCaller.Direct], + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + MaxUses = 1, + Strict = true, + UserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaWebSearchTool20250305 + { + AllowedCallers = [BetaWebSearchTool20250305AllowedCaller.Direct], + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + MaxUses = 1, + Strict = true, + UserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize("\"web_search\""); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_20250305\"" + ); + List> expectedAllowedCallers = + [ + BetaWebSearchTool20250305AllowedCaller.Direct, + ]; + List expectedAllowedDomains = ["string"]; + List expectedBlockedDomains = ["string"]; + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + bool expectedDeferLoading = true; + long expectedMaxUses = 1; + bool expectedStrict = true; + UserLocation expectedUserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedAllowedCallers.Count, deserialized.AllowedCallers.Count); + for (int i = 0; i < expectedAllowedCallers.Count; i++) + { + Assert.Equal(expectedAllowedCallers[i], deserialized.AllowedCallers[i]); + } + Assert.Equal(expectedAllowedDomains.Count, deserialized.AllowedDomains.Count); + for (int i = 0; i < expectedAllowedDomains.Count; i++) + { + Assert.Equal(expectedAllowedDomains[i], deserialized.AllowedDomains[i]); + } + Assert.Equal(expectedBlockedDomains.Count, deserialized.BlockedDomains.Count); + for (int i = 0; i < expectedBlockedDomains.Count; i++) + { + Assert.Equal(expectedBlockedDomains[i], deserialized.BlockedDomains[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDeferLoading, deserialized.DeferLoading); + Assert.Equal(expectedMaxUses, deserialized.MaxUses); + Assert.Equal(expectedStrict, deserialized.Strict); + Assert.Equal(expectedUserLocation, deserialized.UserLocation); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaWebSearchTool20250305 + { + AllowedCallers = [BetaWebSearchTool20250305AllowedCaller.Direct], + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + DeferLoading = true, + MaxUses = 1, + Strict = true, + UserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaWebSearchTool20250305 + { + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + MaxUses = 1, + UserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new BetaWebSearchTool20250305 + { + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + MaxUses = 1, + UserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new BetaWebSearchTool20250305 + { + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + MaxUses = 1, + UserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + Strict = null, + }; + + Assert.Null(model.AllowedCallers); + Assert.False(model.RawData.ContainsKey("allowed_callers")); + Assert.Null(model.DeferLoading); + Assert.False(model.RawData.ContainsKey("defer_loading")); + Assert.Null(model.Strict); + Assert.False(model.RawData.ContainsKey("strict")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaWebSearchTool20250305 + { + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + MaxUses = 1, + UserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }, + + // Null should be interpreted as omitted for these properties + AllowedCallers = null, + DeferLoading = null, + Strict = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaWebSearchTool20250305 + { + AllowedCallers = [BetaWebSearchTool20250305AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + }; + + Assert.Null(model.AllowedDomains); + Assert.False(model.RawData.ContainsKey("allowed_domains")); + Assert.Null(model.BlockedDomains); + Assert.False(model.RawData.ContainsKey("blocked_domains")); + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.MaxUses); + Assert.False(model.RawData.ContainsKey("max_uses")); + Assert.Null(model.UserLocation); + Assert.False(model.RawData.ContainsKey("user_location")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaWebSearchTool20250305 + { + AllowedCallers = [BetaWebSearchTool20250305AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaWebSearchTool20250305 + { + AllowedCallers = [BetaWebSearchTool20250305AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + + AllowedDomains = null, + BlockedDomains = null, + CacheControl = null, + MaxUses = null, + UserLocation = null, + }; + + Assert.Null(model.AllowedDomains); + Assert.True(model.RawData.ContainsKey("allowed_domains")); + Assert.Null(model.BlockedDomains); + Assert.True(model.RawData.ContainsKey("blocked_domains")); + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.MaxUses); + Assert.True(model.RawData.ContainsKey("max_uses")); + Assert.Null(model.UserLocation); + Assert.True(model.RawData.ContainsKey("user_location")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaWebSearchTool20250305 + { + AllowedCallers = [BetaWebSearchTool20250305AllowedCaller.Direct], + DeferLoading = true, + Strict = true, + + AllowedDomains = null, + BlockedDomains = null, + CacheControl = null, + MaxUses = null, + UserLocation = null, + }; + + model.Validate(); + } +} + +public class BetaWebSearchTool20250305AllowedCallerTest : TestBase +{ + [Theory] + [InlineData(BetaWebSearchTool20250305AllowedCaller.Direct)] + [InlineData(BetaWebSearchTool20250305AllowedCaller.CodeExecution20250825)] + public void Validation_Works(BetaWebSearchTool20250305AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaWebSearchTool20250305AllowedCaller.Direct)] + [InlineData(BetaWebSearchTool20250305AllowedCaller.CodeExecution20250825)] + public void SerializationRoundtrip_Works(BetaWebSearchTool20250305AllowedCaller rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize< + ApiEnum + >( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} + +public class UserLocationTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new UserLocation + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"approximate\""); + string expectedCity = "New York"; + string expectedCountry = "US"; + string expectedRegion = "California"; + string expectedTimezone = "America/New_York"; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCity, model.City); + Assert.Equal(expectedCountry, model.Country); + Assert.Equal(expectedRegion, model.Region); + Assert.Equal(expectedTimezone, model.Timezone); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new UserLocation + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new UserLocation + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"approximate\""); + string expectedCity = "New York"; + string expectedCountry = "US"; + string expectedRegion = "California"; + string expectedTimezone = "America/New_York"; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCity, deserialized.City); + Assert.Equal(expectedCountry, deserialized.Country); + Assert.Equal(expectedRegion, deserialized.Region); + Assert.Equal(expectedTimezone, deserialized.Timezone); + } + + [Fact] + public void Validation_Works() + { + var model = new UserLocation + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new UserLocation { }; + + Assert.Null(model.City); + Assert.False(model.RawData.ContainsKey("city")); + Assert.Null(model.Country); + Assert.False(model.RawData.ContainsKey("country")); + Assert.Null(model.Region); + Assert.False(model.RawData.ContainsKey("region")); + Assert.Null(model.Timezone); + Assert.False(model.RawData.ContainsKey("timezone")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new UserLocation { }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new UserLocation + { + City = null, + Country = null, + Region = null, + Timezone = null, + }; + + Assert.Null(model.City); + Assert.True(model.RawData.ContainsKey("city")); + Assert.Null(model.Country); + Assert.True(model.RawData.ContainsKey("country")); + Assert.Null(model.Region); + Assert.True(model.RawData.ContainsKey("region")); + Assert.Null(model.Timezone); + Assert.True(model.RawData.ContainsKey("timezone")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new UserLocation + { + City = null, + Country = null, + Region = null, + Timezone = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolRequestErrorTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolRequestErrorTest.cs new file mode 100644 index 00000000..69911712 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolRequestErrorTest.cs @@ -0,0 +1,73 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebSearchToolRequestErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaWebSearchToolRequestError + { + ErrorCode = BetaWebSearchToolResultErrorCode.InvalidToolInput, + }; + + ApiEnum expectedErrorCode = + BetaWebSearchToolResultErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, model.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaWebSearchToolRequestError + { + ErrorCode = BetaWebSearchToolResultErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaWebSearchToolRequestError + { + ErrorCode = BetaWebSearchToolResultErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ApiEnum expectedErrorCode = + BetaWebSearchToolResultErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, deserialized.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaWebSearchToolRequestError + { + ErrorCode = BetaWebSearchToolResultErrorCode.InvalidToolInput, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultBlockContentTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultBlockContentTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultBlockContentTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultBlockParamContentTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultBlockParamContentTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultBlockParamContentTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultBlockParamTest.cs new file mode 100644 index 00000000..988e85c2 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultBlockParamTest.cs @@ -0,0 +1,240 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebSearchToolResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaWebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + BetaWebSearchToolResultBlockParamContent expectedContent = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result\"" + ); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaWebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaWebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaWebSearchToolResultBlockParamContent expectedContent = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result\"" + ); + BetaCacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaWebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new BetaWebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new BetaWebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new BetaWebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new BetaWebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultBlockTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultBlockTest.cs new file mode 100644 index 00000000..765ec276 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultBlockTest.cs @@ -0,0 +1,90 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebSearchToolResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaWebSearchToolResultBlock + { + Content = new BetaWebSearchToolResultError( + BetaWebSearchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + BetaWebSearchToolResultBlockContent expectedContent = new BetaWebSearchToolResultError( + BetaWebSearchToolResultErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result\"" + ); + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaWebSearchToolResultBlock + { + Content = new BetaWebSearchToolResultError( + BetaWebSearchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaWebSearchToolResultBlock + { + Content = new BetaWebSearchToolResultError( + BetaWebSearchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + BetaWebSearchToolResultBlockContent expectedContent = new BetaWebSearchToolResultError( + BetaWebSearchToolResultErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result\"" + ); + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaWebSearchToolResultBlock + { + Content = new BetaWebSearchToolResultError( + BetaWebSearchToolResultErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultErrorCodeTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultErrorCodeTest.cs new file mode 100644 index 00000000..100949dd --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultErrorCodeTest.cs @@ -0,0 +1,66 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebSearchToolResultErrorCodeTest : TestBase +{ + [Theory] + [InlineData(BetaWebSearchToolResultErrorCode.InvalidToolInput)] + [InlineData(BetaWebSearchToolResultErrorCode.Unavailable)] + [InlineData(BetaWebSearchToolResultErrorCode.MaxUsesExceeded)] + [InlineData(BetaWebSearchToolResultErrorCode.TooManyRequests)] + [InlineData(BetaWebSearchToolResultErrorCode.QueryTooLong)] + public void Validation_Works(BetaWebSearchToolResultErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(BetaWebSearchToolResultErrorCode.InvalidToolInput)] + [InlineData(BetaWebSearchToolResultErrorCode.Unavailable)] + [InlineData(BetaWebSearchToolResultErrorCode.MaxUsesExceeded)] + [InlineData(BetaWebSearchToolResultErrorCode.TooManyRequests)] + [InlineData(BetaWebSearchToolResultErrorCode.QueryTooLong)] + public void SerializationRoundtrip_Works(BetaWebSearchToolResultErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultErrorTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultErrorTest.cs new file mode 100644 index 00000000..b16ac47d --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/BetaWebSearchToolResultErrorTest.cs @@ -0,0 +1,73 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class BetaWebSearchToolResultErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaWebSearchToolResultError + { + ErrorCode = BetaWebSearchToolResultErrorCode.InvalidToolInput, + }; + + ApiEnum expectedErrorCode = + BetaWebSearchToolResultErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, model.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaWebSearchToolResultError + { + ErrorCode = BetaWebSearchToolResultErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaWebSearchToolResultError + { + ErrorCode = BetaWebSearchToolResultErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ApiEnum expectedErrorCode = + BetaWebSearchToolResultErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, deserialized.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaWebSearchToolResultError + { + ErrorCode = BetaWebSearchToolResultErrorCode.InvalidToolInput, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Messages/MessageBetaContentBlockSourceContentTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/MessageBetaContentBlockSourceContentTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/MessageBetaContentBlockSourceContentTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/MessageCountTokensParamsTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/MessageCountTokensParamsTest.cs new file mode 100644 index 00000000..3cc637ca --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/MessageCountTokensParamsTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Beta.Messages; diff --git a/src/Anthropic.Tests/Models/Beta/Messages/MessageCreateParamsTest.cs b/src/Anthropic.Tests/Models/Beta/Messages/MessageCreateParamsTest.cs new file mode 100644 index 00000000..e33afc14 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Messages/MessageCreateParamsTest.cs @@ -0,0 +1,62 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Beta.Messages; + +namespace Anthropic.Tests.Models.Beta.Messages; + +public class ServiceTierTest : TestBase +{ + [Theory] + [InlineData(ServiceTier.Auto)] + [InlineData(ServiceTier.StandardOnly)] + public void Validation_Works(ServiceTier rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(ServiceTier.Auto)] + [InlineData(ServiceTier.StandardOnly)] + public void SerializationRoundtrip_Works(ServiceTier rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Models/BetaModelInfoTest.cs b/src/Anthropic.Tests/Models/Beta/Models/BetaModelInfoTest.cs new file mode 100644 index 00000000..25399993 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Models/BetaModelInfoTest.cs @@ -0,0 +1,83 @@ +using System; +using System.Text.Json; +using Anthropic.Models.Beta.Models; + +namespace Anthropic.Tests.Models.Beta.Models; + +public class BetaModelInfoTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BetaModelInfo + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }; + + string expectedID = "claude-sonnet-4-20250514"; + DateTimeOffset expectedCreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"); + string expectedDisplayName = "Claude Sonnet 4"; + JsonElement expectedType = JsonSerializer.Deserialize("\"model\""); + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedCreatedAt, model.CreatedAt); + Assert.Equal(expectedDisplayName, model.DisplayName); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BetaModelInfo + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BetaModelInfo + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "claude-sonnet-4-20250514"; + DateTimeOffset expectedCreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"); + string expectedDisplayName = "Claude Sonnet 4"; + JsonElement expectedType = JsonSerializer.Deserialize("\"model\""); + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedCreatedAt, deserialized.CreatedAt); + Assert.Equal(expectedDisplayName, deserialized.DisplayName); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BetaModelInfo + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Models/ModelListPageResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Models/ModelListPageResponseTest.cs new file mode 100644 index 00000000..47bb216b --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Models/ModelListPageResponseTest.cs @@ -0,0 +1,144 @@ +using System; +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Models; + +namespace Anthropic.Tests.Models.Beta.Models; + +public class ModelListPageResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ModelListPageResponse + { + Data = + [ + new() + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + List expectedData = + [ + new() + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }, + ]; + string expectedFirstID = "first_id"; + bool expectedHasMore = true; + string expectedLastID = "last_id"; + + Assert.Equal(expectedData.Count, model.Data.Count); + for (int i = 0; i < expectedData.Count; i++) + { + Assert.Equal(expectedData[i], model.Data[i]); + } + Assert.Equal(expectedFirstID, model.FirstID); + Assert.Equal(expectedHasMore, model.HasMore); + Assert.Equal(expectedLastID, model.LastID); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ModelListPageResponse + { + Data = + [ + new() + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ModelListPageResponse + { + Data = + [ + new() + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedData = + [ + new() + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }, + ]; + string expectedFirstID = "first_id"; + bool expectedHasMore = true; + string expectedLastID = "last_id"; + + Assert.Equal(expectedData.Count, deserialized.Data.Count); + for (int i = 0; i < expectedData.Count; i++) + { + Assert.Equal(expectedData[i], deserialized.Data[i]); + } + Assert.Equal(expectedFirstID, deserialized.FirstID); + Assert.Equal(expectedHasMore, deserialized.HasMore); + Assert.Equal(expectedLastID, deserialized.LastID); + } + + [Fact] + public void Validation_Works() + { + var model = new ModelListPageResponse + { + Data = + [ + new() + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Skills/SkillCreateResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Skills/SkillCreateResponseTest.cs new file mode 100644 index 00000000..b010b815 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Skills/SkillCreateResponseTest.cs @@ -0,0 +1,110 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Skills; + +namespace Anthropic.Tests.Models.Beta.Skills; + +public class SkillCreateResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new SkillCreateResponse + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }; + + string expectedID = "skill_01JAbcdefghijklmnopqrstuvw"; + string expectedCreatedAt = "2024-10-30T23:58:27.427722Z"; + string expectedDisplayTitle = "My Custom Skill"; + string expectedLatestVersion = "1759178010641129"; + string expectedSource = "custom"; + string expectedType = "type"; + string expectedUpdatedAt = "2024-10-30T23:58:27.427722Z"; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedCreatedAt, model.CreatedAt); + Assert.Equal(expectedDisplayTitle, model.DisplayTitle); + Assert.Equal(expectedLatestVersion, model.LatestVersion); + Assert.Equal(expectedSource, model.Source); + Assert.Equal(expectedType, model.Type); + Assert.Equal(expectedUpdatedAt, model.UpdatedAt); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new SkillCreateResponse + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new SkillCreateResponse + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "skill_01JAbcdefghijklmnopqrstuvw"; + string expectedCreatedAt = "2024-10-30T23:58:27.427722Z"; + string expectedDisplayTitle = "My Custom Skill"; + string expectedLatestVersion = "1759178010641129"; + string expectedSource = "custom"; + string expectedType = "type"; + string expectedUpdatedAt = "2024-10-30T23:58:27.427722Z"; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedCreatedAt, deserialized.CreatedAt); + Assert.Equal(expectedDisplayTitle, deserialized.DisplayTitle); + Assert.Equal(expectedLatestVersion, deserialized.LatestVersion); + Assert.Equal(expectedSource, deserialized.Source); + Assert.Equal(expectedType, deserialized.Type); + Assert.Equal(expectedUpdatedAt, deserialized.UpdatedAt); + } + + [Fact] + public void Validation_Works() + { + var model = new SkillCreateResponse + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Skills/SkillDeleteResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Skills/SkillDeleteResponseTest.cs new file mode 100644 index 00000000..af0d7ce5 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Skills/SkillDeleteResponseTest.cs @@ -0,0 +1,70 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Skills; + +namespace Anthropic.Tests.Models.Beta.Skills; + +public class SkillDeleteResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new SkillDeleteResponse + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + }; + + string expectedID = "skill_01JAbcdefghijklmnopqrstuvw"; + string expectedType = "type"; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedType, model.Type); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new SkillDeleteResponse + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new SkillDeleteResponse + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "skill_01JAbcdefghijklmnopqrstuvw"; + string expectedType = "type"; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedType, deserialized.Type); + } + + [Fact] + public void Validation_Works() + { + var model = new SkillDeleteResponse + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Skills/SkillListPageResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Skills/SkillListPageResponseTest.cs new file mode 100644 index 00000000..546edda9 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Skills/SkillListPageResponseTest.cs @@ -0,0 +1,265 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Skills; + +namespace Anthropic.Tests.Models.Beta.Skills; + +public class SkillListPageResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new SkillListPageResponse + { + Data = + [ + new() + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }, + ], + HasMore = true, + NextPage = "page_MjAyNS0wNS0xNFQwMDowMDowMFo=", + }; + + List expectedData = + [ + new() + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }, + ]; + bool expectedHasMore = true; + string expectedNextPage = "page_MjAyNS0wNS0xNFQwMDowMDowMFo="; + + Assert.Equal(expectedData.Count, model.Data.Count); + for (int i = 0; i < expectedData.Count; i++) + { + Assert.Equal(expectedData[i], model.Data[i]); + } + Assert.Equal(expectedHasMore, model.HasMore); + Assert.Equal(expectedNextPage, model.NextPage); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new SkillListPageResponse + { + Data = + [ + new() + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }, + ], + HasMore = true, + NextPage = "page_MjAyNS0wNS0xNFQwMDowMDowMFo=", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new SkillListPageResponse + { + Data = + [ + new() + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }, + ], + HasMore = true, + NextPage = "page_MjAyNS0wNS0xNFQwMDowMDowMFo=", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedData = + [ + new() + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }, + ]; + bool expectedHasMore = true; + string expectedNextPage = "page_MjAyNS0wNS0xNFQwMDowMDowMFo="; + + Assert.Equal(expectedData.Count, deserialized.Data.Count); + for (int i = 0; i < expectedData.Count; i++) + { + Assert.Equal(expectedData[i], deserialized.Data[i]); + } + Assert.Equal(expectedHasMore, deserialized.HasMore); + Assert.Equal(expectedNextPage, deserialized.NextPage); + } + + [Fact] + public void Validation_Works() + { + var model = new SkillListPageResponse + { + Data = + [ + new() + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }, + ], + HasMore = true, + NextPage = "page_MjAyNS0wNS0xNFQwMDowMDowMFo=", + }; + + model.Validate(); + } +} + +public class DataTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Data + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }; + + string expectedID = "skill_01JAbcdefghijklmnopqrstuvw"; + string expectedCreatedAt = "2024-10-30T23:58:27.427722Z"; + string expectedDisplayTitle = "My Custom Skill"; + string expectedLatestVersion = "1759178010641129"; + string expectedSource = "custom"; + string expectedType = "type"; + string expectedUpdatedAt = "2024-10-30T23:58:27.427722Z"; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedCreatedAt, model.CreatedAt); + Assert.Equal(expectedDisplayTitle, model.DisplayTitle); + Assert.Equal(expectedLatestVersion, model.LatestVersion); + Assert.Equal(expectedSource, model.Source); + Assert.Equal(expectedType, model.Type); + Assert.Equal(expectedUpdatedAt, model.UpdatedAt); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Data + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Data + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "skill_01JAbcdefghijklmnopqrstuvw"; + string expectedCreatedAt = "2024-10-30T23:58:27.427722Z"; + string expectedDisplayTitle = "My Custom Skill"; + string expectedLatestVersion = "1759178010641129"; + string expectedSource = "custom"; + string expectedType = "type"; + string expectedUpdatedAt = "2024-10-30T23:58:27.427722Z"; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedCreatedAt, deserialized.CreatedAt); + Assert.Equal(expectedDisplayTitle, deserialized.DisplayTitle); + Assert.Equal(expectedLatestVersion, deserialized.LatestVersion); + Assert.Equal(expectedSource, deserialized.Source); + Assert.Equal(expectedType, deserialized.Type); + Assert.Equal(expectedUpdatedAt, deserialized.UpdatedAt); + } + + [Fact] + public void Validation_Works() + { + var model = new Data + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Skills/SkillRetrieveResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Skills/SkillRetrieveResponseTest.cs new file mode 100644 index 00000000..221156a3 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Skills/SkillRetrieveResponseTest.cs @@ -0,0 +1,110 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Skills; + +namespace Anthropic.Tests.Models.Beta.Skills; + +public class SkillRetrieveResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new SkillRetrieveResponse + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }; + + string expectedID = "skill_01JAbcdefghijklmnopqrstuvw"; + string expectedCreatedAt = "2024-10-30T23:58:27.427722Z"; + string expectedDisplayTitle = "My Custom Skill"; + string expectedLatestVersion = "1759178010641129"; + string expectedSource = "custom"; + string expectedType = "type"; + string expectedUpdatedAt = "2024-10-30T23:58:27.427722Z"; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedCreatedAt, model.CreatedAt); + Assert.Equal(expectedDisplayTitle, model.DisplayTitle); + Assert.Equal(expectedLatestVersion, model.LatestVersion); + Assert.Equal(expectedSource, model.Source); + Assert.Equal(expectedType, model.Type); + Assert.Equal(expectedUpdatedAt, model.UpdatedAt); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new SkillRetrieveResponse + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new SkillRetrieveResponse + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "skill_01JAbcdefghijklmnopqrstuvw"; + string expectedCreatedAt = "2024-10-30T23:58:27.427722Z"; + string expectedDisplayTitle = "My Custom Skill"; + string expectedLatestVersion = "1759178010641129"; + string expectedSource = "custom"; + string expectedType = "type"; + string expectedUpdatedAt = "2024-10-30T23:58:27.427722Z"; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedCreatedAt, deserialized.CreatedAt); + Assert.Equal(expectedDisplayTitle, deserialized.DisplayTitle); + Assert.Equal(expectedLatestVersion, deserialized.LatestVersion); + Assert.Equal(expectedSource, deserialized.Source); + Assert.Equal(expectedType, deserialized.Type); + Assert.Equal(expectedUpdatedAt, deserialized.UpdatedAt); + } + + [Fact] + public void Validation_Works() + { + var model = new SkillRetrieveResponse + { + ID = "skill_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + DisplayTitle = "My Custom Skill", + LatestVersion = "1759178010641129", + Source = "custom", + Type = "type", + UpdatedAt = "2024-10-30T23:58:27.427722Z", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Skills/Versions/VersionCreateResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Skills/Versions/VersionCreateResponseTest.cs new file mode 100644 index 00000000..834aae0c --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Skills/Versions/VersionCreateResponseTest.cs @@ -0,0 +1,118 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Skills.Versions; + +namespace Anthropic.Tests.Models.Beta.Skills.Versions; + +public class VersionCreateResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new VersionCreateResponse + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }; + + string expectedID = "skillver_01JAbcdefghijklmnopqrstuvw"; + string expectedCreatedAt = "2024-10-30T23:58:27.427722Z"; + string expectedDescription = "A custom skill for doing something useful"; + string expectedDirectory = "my-skill"; + string expectedName = "my-skill"; + string expectedSkillID = "skill_01JAbcdefghijklmnopqrstuvw"; + string expectedType = "type"; + string expectedVersion = "1759178010641129"; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedCreatedAt, model.CreatedAt); + Assert.Equal(expectedDescription, model.Description); + Assert.Equal(expectedDirectory, model.Directory); + Assert.Equal(expectedName, model.Name); + Assert.Equal(expectedSkillID, model.SkillID); + Assert.Equal(expectedType, model.Type); + Assert.Equal(expectedVersion, model.Version); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new VersionCreateResponse + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new VersionCreateResponse + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "skillver_01JAbcdefghijklmnopqrstuvw"; + string expectedCreatedAt = "2024-10-30T23:58:27.427722Z"; + string expectedDescription = "A custom skill for doing something useful"; + string expectedDirectory = "my-skill"; + string expectedName = "my-skill"; + string expectedSkillID = "skill_01JAbcdefghijklmnopqrstuvw"; + string expectedType = "type"; + string expectedVersion = "1759178010641129"; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedCreatedAt, deserialized.CreatedAt); + Assert.Equal(expectedDescription, deserialized.Description); + Assert.Equal(expectedDirectory, deserialized.Directory); + Assert.Equal(expectedName, deserialized.Name); + Assert.Equal(expectedSkillID, deserialized.SkillID); + Assert.Equal(expectedType, deserialized.Type); + Assert.Equal(expectedVersion, deserialized.Version); + } + + [Fact] + public void Validation_Works() + { + var model = new VersionCreateResponse + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Skills/Versions/VersionDeleteResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Skills/Versions/VersionDeleteResponseTest.cs new file mode 100644 index 00000000..a660d32e --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Skills/Versions/VersionDeleteResponseTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Skills.Versions; + +namespace Anthropic.Tests.Models.Beta.Skills.Versions; + +public class VersionDeleteResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new VersionDeleteResponse { ID = "1759178010641129", Type = "type" }; + + string expectedID = "1759178010641129"; + string expectedType = "type"; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedType, model.Type); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new VersionDeleteResponse { ID = "1759178010641129", Type = "type" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new VersionDeleteResponse { ID = "1759178010641129", Type = "type" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "1759178010641129"; + string expectedType = "type"; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedType, deserialized.Type); + } + + [Fact] + public void Validation_Works() + { + var model = new VersionDeleteResponse { ID = "1759178010641129", Type = "type" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Skills/Versions/VersionListPageResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Skills/Versions/VersionListPageResponseTest.cs new file mode 100644 index 00000000..e8126aa9 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Skills/Versions/VersionListPageResponseTest.cs @@ -0,0 +1,279 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Beta.Skills.Versions; + +namespace Anthropic.Tests.Models.Beta.Skills.Versions; + +public class VersionListPageResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new VersionListPageResponse + { + Data = + [ + new() + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }, + ], + HasMore = true, + NextPage = "page_MjAyNS0wNS0xNFQwMDowMDowMFo=", + }; + + List expectedData = + [ + new() + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }, + ]; + bool expectedHasMore = true; + string expectedNextPage = "page_MjAyNS0wNS0xNFQwMDowMDowMFo="; + + Assert.Equal(expectedData.Count, model.Data.Count); + for (int i = 0; i < expectedData.Count; i++) + { + Assert.Equal(expectedData[i], model.Data[i]); + } + Assert.Equal(expectedHasMore, model.HasMore); + Assert.Equal(expectedNextPage, model.NextPage); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new VersionListPageResponse + { + Data = + [ + new() + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }, + ], + HasMore = true, + NextPage = "page_MjAyNS0wNS0xNFQwMDowMDowMFo=", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new VersionListPageResponse + { + Data = + [ + new() + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }, + ], + HasMore = true, + NextPage = "page_MjAyNS0wNS0xNFQwMDowMDowMFo=", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedData = + [ + new() + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }, + ]; + bool expectedHasMore = true; + string expectedNextPage = "page_MjAyNS0wNS0xNFQwMDowMDowMFo="; + + Assert.Equal(expectedData.Count, deserialized.Data.Count); + for (int i = 0; i < expectedData.Count; i++) + { + Assert.Equal(expectedData[i], deserialized.Data[i]); + } + Assert.Equal(expectedHasMore, deserialized.HasMore); + Assert.Equal(expectedNextPage, deserialized.NextPage); + } + + [Fact] + public void Validation_Works() + { + var model = new VersionListPageResponse + { + Data = + [ + new() + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }, + ], + HasMore = true, + NextPage = "page_MjAyNS0wNS0xNFQwMDowMDowMFo=", + }; + + model.Validate(); + } +} + +public class DataTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Data + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }; + + string expectedID = "skillver_01JAbcdefghijklmnopqrstuvw"; + string expectedCreatedAt = "2024-10-30T23:58:27.427722Z"; + string expectedDescription = "A custom skill for doing something useful"; + string expectedDirectory = "my-skill"; + string expectedName = "my-skill"; + string expectedSkillID = "skill_01JAbcdefghijklmnopqrstuvw"; + string expectedType = "type"; + string expectedVersion = "1759178010641129"; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedCreatedAt, model.CreatedAt); + Assert.Equal(expectedDescription, model.Description); + Assert.Equal(expectedDirectory, model.Directory); + Assert.Equal(expectedName, model.Name); + Assert.Equal(expectedSkillID, model.SkillID); + Assert.Equal(expectedType, model.Type); + Assert.Equal(expectedVersion, model.Version); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Data + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Data + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "skillver_01JAbcdefghijklmnopqrstuvw"; + string expectedCreatedAt = "2024-10-30T23:58:27.427722Z"; + string expectedDescription = "A custom skill for doing something useful"; + string expectedDirectory = "my-skill"; + string expectedName = "my-skill"; + string expectedSkillID = "skill_01JAbcdefghijklmnopqrstuvw"; + string expectedType = "type"; + string expectedVersion = "1759178010641129"; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedCreatedAt, deserialized.CreatedAt); + Assert.Equal(expectedDescription, deserialized.Description); + Assert.Equal(expectedDirectory, deserialized.Directory); + Assert.Equal(expectedName, deserialized.Name); + Assert.Equal(expectedSkillID, deserialized.SkillID); + Assert.Equal(expectedType, deserialized.Type); + Assert.Equal(expectedVersion, deserialized.Version); + } + + [Fact] + public void Validation_Works() + { + var model = new Data + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Beta/Skills/Versions/VersionRetrieveResponseTest.cs b/src/Anthropic.Tests/Models/Beta/Skills/Versions/VersionRetrieveResponseTest.cs new file mode 100644 index 00000000..92c39fc8 --- /dev/null +++ b/src/Anthropic.Tests/Models/Beta/Skills/Versions/VersionRetrieveResponseTest.cs @@ -0,0 +1,118 @@ +using System.Text.Json; +using Anthropic.Models.Beta.Skills.Versions; + +namespace Anthropic.Tests.Models.Beta.Skills.Versions; + +public class VersionRetrieveResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new VersionRetrieveResponse + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }; + + string expectedID = "skillver_01JAbcdefghijklmnopqrstuvw"; + string expectedCreatedAt = "2024-10-30T23:58:27.427722Z"; + string expectedDescription = "A custom skill for doing something useful"; + string expectedDirectory = "my-skill"; + string expectedName = "my-skill"; + string expectedSkillID = "skill_01JAbcdefghijklmnopqrstuvw"; + string expectedType = "type"; + string expectedVersion = "1759178010641129"; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedCreatedAt, model.CreatedAt); + Assert.Equal(expectedDescription, model.Description); + Assert.Equal(expectedDirectory, model.Directory); + Assert.Equal(expectedName, model.Name); + Assert.Equal(expectedSkillID, model.SkillID); + Assert.Equal(expectedType, model.Type); + Assert.Equal(expectedVersion, model.Version); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new VersionRetrieveResponse + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new VersionRetrieveResponse + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "skillver_01JAbcdefghijklmnopqrstuvw"; + string expectedCreatedAt = "2024-10-30T23:58:27.427722Z"; + string expectedDescription = "A custom skill for doing something useful"; + string expectedDirectory = "my-skill"; + string expectedName = "my-skill"; + string expectedSkillID = "skill_01JAbcdefghijklmnopqrstuvw"; + string expectedType = "type"; + string expectedVersion = "1759178010641129"; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedCreatedAt, deserialized.CreatedAt); + Assert.Equal(expectedDescription, deserialized.Description); + Assert.Equal(expectedDirectory, deserialized.Directory); + Assert.Equal(expectedName, deserialized.Name); + Assert.Equal(expectedSkillID, deserialized.SkillID); + Assert.Equal(expectedType, deserialized.Type); + Assert.Equal(expectedVersion, deserialized.Version); + } + + [Fact] + public void Validation_Works() + { + var model = new VersionRetrieveResponse + { + ID = "skillver_01JAbcdefghijklmnopqrstuvw", + CreatedAt = "2024-10-30T23:58:27.427722Z", + Description = "A custom skill for doing something useful", + Directory = "my-skill", + Name = "my-skill", + SkillID = "skill_01JAbcdefghijklmnopqrstuvw", + Type = "type", + Version = "1759178010641129", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/BillingErrorTest.cs b/src/Anthropic.Tests/Models/BillingErrorTest.cs new file mode 100644 index 00000000..0f71b978 --- /dev/null +++ b/src/Anthropic.Tests/Models/BillingErrorTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models; + +namespace Anthropic.Tests.Models; + +public class BillingErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BillingError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"billing_error\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BillingError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BillingError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"billing_error\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new BillingError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/ErrorObjectTest.cs b/src/Anthropic.Tests/Models/ErrorObjectTest.cs new file mode 100644 index 00000000..2e7941ef --- /dev/null +++ b/src/Anthropic.Tests/Models/ErrorObjectTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models; diff --git a/src/Anthropic.Tests/Models/ErrorResponseTest.cs b/src/Anthropic.Tests/Models/ErrorResponseTest.cs new file mode 100644 index 00000000..65bc421c --- /dev/null +++ b/src/Anthropic.Tests/Models/ErrorResponseTest.cs @@ -0,0 +1,74 @@ +using System.Text.Json; +using Anthropic.Models; + +namespace Anthropic.Tests.Models; + +public class ErrorResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ErrorResponse + { + Error = new InvalidRequestError("message"), + RequestID = "request_id", + }; + + ErrorObject expectedError = new InvalidRequestError("message"); + string expectedRequestID = "request_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"error\""); + + Assert.Equal(expectedError, model.Error); + Assert.Equal(expectedRequestID, model.RequestID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ErrorResponse + { + Error = new InvalidRequestError("message"), + RequestID = "request_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ErrorResponse + { + Error = new InvalidRequestError("message"), + RequestID = "request_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ErrorObject expectedError = new InvalidRequestError("message"); + string expectedRequestID = "request_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"error\""); + + Assert.Equal(expectedError, deserialized.Error); + Assert.Equal(expectedRequestID, deserialized.RequestID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new ErrorResponse + { + Error = new InvalidRequestError("message"), + RequestID = "request_id", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/GatewayTimeoutErrorTest.cs b/src/Anthropic.Tests/Models/GatewayTimeoutErrorTest.cs new file mode 100644 index 00000000..8a1e665e --- /dev/null +++ b/src/Anthropic.Tests/Models/GatewayTimeoutErrorTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models; + +namespace Anthropic.Tests.Models; + +public class GatewayTimeoutErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new GatewayTimeoutError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"timeout_error\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new GatewayTimeoutError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new GatewayTimeoutError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"timeout_error\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new GatewayTimeoutError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/InvalidRequestErrorTest.cs b/src/Anthropic.Tests/Models/InvalidRequestErrorTest.cs new file mode 100644 index 00000000..87b9740d --- /dev/null +++ b/src/Anthropic.Tests/Models/InvalidRequestErrorTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models; + +namespace Anthropic.Tests.Models; + +public class InvalidRequestErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new InvalidRequestError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"invalid_request_error\"" + ); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new InvalidRequestError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new InvalidRequestError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"invalid_request_error\"" + ); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new InvalidRequestError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/Base64ImageSourceTest.cs b/src/Anthropic.Tests/Models/Messages/Base64ImageSourceTest.cs new file mode 100644 index 00000000..f7a372a2 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/Base64ImageSourceTest.cs @@ -0,0 +1,136 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class Base64ImageSourceTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Base64ImageSource + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }; + + string expectedData = "U3RhaW5sZXNzIHJvY2tz"; + ApiEnum expectedMediaType = MediaType.ImageJPEG; + JsonElement expectedType = JsonSerializer.Deserialize("\"base64\""); + + Assert.Equal(expectedData, model.Data); + Assert.Equal(expectedMediaType, model.MediaType); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Base64ImageSource + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Base64ImageSource + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedData = "U3RhaW5sZXNzIHJvY2tz"; + ApiEnum expectedMediaType = MediaType.ImageJPEG; + JsonElement expectedType = JsonSerializer.Deserialize("\"base64\""); + + Assert.Equal(expectedData, deserialized.Data); + Assert.Equal(expectedMediaType, deserialized.MediaType); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new Base64ImageSource + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }; + + model.Validate(); + } +} + +public class MediaTypeTest : TestBase +{ + [Theory] + [InlineData(MediaType.ImageJPEG)] + [InlineData(MediaType.ImagePNG)] + [InlineData(MediaType.ImageGIF)] + [InlineData(MediaType.ImageWebP)] + public void Validation_Works(MediaType rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(MediaType.ImageJPEG)] + [InlineData(MediaType.ImagePNG)] + [InlineData(MediaType.ImageGIF)] + [InlineData(MediaType.ImageWebP)] + public void SerializationRoundtrip_Works(MediaType rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/Base64PDFSourceTest.cs b/src/Anthropic.Tests/Models/Messages/Base64PDFSourceTest.cs new file mode 100644 index 00000000..b863b572 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/Base64PDFSourceTest.cs @@ -0,0 +1,62 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class Base64PDFSourceTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Base64PDFSource { Data = "U3RhaW5sZXNzIHJvY2tz" }; + + string expectedData = "U3RhaW5sZXNzIHJvY2tz"; + JsonElement expectedMediaType = JsonSerializer.Deserialize( + "\"application/pdf\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize("\"base64\""); + + Assert.Equal(expectedData, model.Data); + Assert.True(JsonElement.DeepEquals(expectedMediaType, model.MediaType)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Base64PDFSource { Data = "U3RhaW5sZXNzIHJvY2tz" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Base64PDFSource { Data = "U3RhaW5sZXNzIHJvY2tz" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedData = "U3RhaW5sZXNzIHJvY2tz"; + JsonElement expectedMediaType = JsonSerializer.Deserialize( + "\"application/pdf\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize("\"base64\""); + + Assert.Equal(expectedData, deserialized.Data); + Assert.True(JsonElement.DeepEquals(expectedMediaType, deserialized.MediaType)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new Base64PDFSource { Data = "U3RhaW5sZXNzIHJvY2tz" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/Batches/BatchCreateParamsTest.cs b/src/Anthropic.Tests/Models/Messages/Batches/BatchCreateParamsTest.cs new file mode 100644 index 00000000..e4557eed --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/Batches/BatchCreateParamsTest.cs @@ -0,0 +1,994 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Messages.Batches; +using Messages = Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages.Batches; + +public class RequestTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Request + { + CustomID = "my-custom-id-1", + Params = new() + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = Messages::Model.ClaudeOpus4_5_20251101, + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::ThinkingConfigEnabled(1024), + ToolChoice = new Messages::ToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::Tool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Messages::Type.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }, + }; + + string expectedCustomID = "my-custom-id-1"; + Params expectedParams = new() + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = Messages::Model.ClaudeOpus4_5_20251101, + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::ThinkingConfigEnabled(1024), + ToolChoice = new Messages::ToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::Tool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Messages::Type.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }; + + Assert.Equal(expectedCustomID, model.CustomID); + Assert.Equal(expectedParams, model.Params); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Request + { + CustomID = "my-custom-id-1", + Params = new() + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = Messages::Model.ClaudeOpus4_5_20251101, + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::ThinkingConfigEnabled(1024), + ToolChoice = new Messages::ToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::Tool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Messages::Type.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Request + { + CustomID = "my-custom-id-1", + Params = new() + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = Messages::Model.ClaudeOpus4_5_20251101, + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::ThinkingConfigEnabled(1024), + ToolChoice = new Messages::ToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::Tool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Messages::Type.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCustomID = "my-custom-id-1"; + Params expectedParams = new() + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = Messages::Model.ClaudeOpus4_5_20251101, + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::ThinkingConfigEnabled(1024), + ToolChoice = new Messages::ToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::Tool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Messages::Type.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }; + + Assert.Equal(expectedCustomID, deserialized.CustomID); + Assert.Equal(expectedParams, deserialized.Params); + } + + [Fact] + public void Validation_Works() + { + var model = new Request + { + CustomID = "my-custom-id-1", + Params = new() + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = Messages::Model.ClaudeOpus4_5_20251101, + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::ThinkingConfigEnabled(1024), + ToolChoice = new Messages::ToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::Tool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Messages::Type.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }, + }; + + model.Validate(); + } +} + +public class ParamsTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = Messages::Model.ClaudeOpus4_5_20251101, + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::ThinkingConfigEnabled(1024), + ToolChoice = new Messages::ToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::Tool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Messages::Type.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }; + + long expectedMaxTokens = 1024; + List expectedMessages = + [ + new() { Content = "Hello, world", Role = Messages::Role.User }, + ]; + ApiEnum expectedModel = Messages::Model.ClaudeOpus4_5_20251101; + Messages::Metadata expectedMetadata = new() + { + UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b", + }; + ApiEnum expectedServiceTier = ServiceTier.Auto; + List expectedStopSequences = ["string"]; + bool expectedStream = true; + ParamsSystem expectedSystem = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ); + double expectedTemperature = 1; + Messages::ThinkingConfigParam expectedThinking = new Messages::ThinkingConfigEnabled(1024); + Messages::ToolChoice expectedToolChoice = new Messages::ToolChoiceAuto() + { + DisableParallelToolUse = true, + }; + List expectedTools = + [ + new Messages::Tool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Messages::Type.Custom, + }, + ]; + long expectedTopK = 5; + double expectedTopP = 0.7; + + Assert.Equal(expectedMaxTokens, model.MaxTokens); + Assert.Equal(expectedMessages.Count, model.Messages.Count); + for (int i = 0; i < expectedMessages.Count; i++) + { + Assert.Equal(expectedMessages[i], model.Messages[i]); + } + Assert.Equal(expectedModel, model.Model); + Assert.Equal(expectedMetadata, model.Metadata); + Assert.Equal(expectedServiceTier, model.ServiceTier); + Assert.Equal(expectedStopSequences.Count, model.StopSequences.Count); + for (int i = 0; i < expectedStopSequences.Count; i++) + { + Assert.Equal(expectedStopSequences[i], model.StopSequences[i]); + } + Assert.Equal(expectedStream, model.Stream); + Assert.Equal(expectedSystem, model.System); + Assert.Equal(expectedTemperature, model.Temperature); + Assert.Equal(expectedThinking, model.Thinking); + Assert.Equal(expectedToolChoice, model.ToolChoice); + Assert.Equal(expectedTools.Count, model.Tools.Count); + for (int i = 0; i < expectedTools.Count; i++) + { + Assert.Equal(expectedTools[i], model.Tools[i]); + } + Assert.Equal(expectedTopK, model.TopK); + Assert.Equal(expectedTopP, model.TopP); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = Messages::Model.ClaudeOpus4_5_20251101, + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::ThinkingConfigEnabled(1024), + ToolChoice = new Messages::ToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::Tool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Messages::Type.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = Messages::Model.ClaudeOpus4_5_20251101, + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::ThinkingConfigEnabled(1024), + ToolChoice = new Messages::ToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::Tool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Messages::Type.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedMaxTokens = 1024; + List expectedMessages = + [ + new() { Content = "Hello, world", Role = Messages::Role.User }, + ]; + ApiEnum expectedModel = Messages::Model.ClaudeOpus4_5_20251101; + Messages::Metadata expectedMetadata = new() + { + UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b", + }; + ApiEnum expectedServiceTier = ServiceTier.Auto; + List expectedStopSequences = ["string"]; + bool expectedStream = true; + ParamsSystem expectedSystem = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ); + double expectedTemperature = 1; + Messages::ThinkingConfigParam expectedThinking = new Messages::ThinkingConfigEnabled(1024); + Messages::ToolChoice expectedToolChoice = new Messages::ToolChoiceAuto() + { + DisableParallelToolUse = true, + }; + List expectedTools = + [ + new Messages::Tool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Messages::Type.Custom, + }, + ]; + long expectedTopK = 5; + double expectedTopP = 0.7; + + Assert.Equal(expectedMaxTokens, deserialized.MaxTokens); + Assert.Equal(expectedMessages.Count, deserialized.Messages.Count); + for (int i = 0; i < expectedMessages.Count; i++) + { + Assert.Equal(expectedMessages[i], deserialized.Messages[i]); + } + Assert.Equal(expectedModel, deserialized.Model); + Assert.Equal(expectedMetadata, deserialized.Metadata); + Assert.Equal(expectedServiceTier, deserialized.ServiceTier); + Assert.Equal(expectedStopSequences.Count, deserialized.StopSequences.Count); + for (int i = 0; i < expectedStopSequences.Count; i++) + { + Assert.Equal(expectedStopSequences[i], deserialized.StopSequences[i]); + } + Assert.Equal(expectedStream, deserialized.Stream); + Assert.Equal(expectedSystem, deserialized.System); + Assert.Equal(expectedTemperature, deserialized.Temperature); + Assert.Equal(expectedThinking, deserialized.Thinking); + Assert.Equal(expectedToolChoice, deserialized.ToolChoice); + Assert.Equal(expectedTools.Count, deserialized.Tools.Count); + for (int i = 0; i < expectedTools.Count; i++) + { + Assert.Equal(expectedTools[i], deserialized.Tools[i]); + } + Assert.Equal(expectedTopK, deserialized.TopK); + Assert.Equal(expectedTopP, deserialized.TopP); + } + + [Fact] + public void Validation_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = Messages::Model.ClaudeOpus4_5_20251101, + Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, + ServiceTier = ServiceTier.Auto, + StopSequences = ["string"], + Stream = true, + System = new( + [ + new() + { + Text = "Today's date is 2024-06-01.", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Citations = + [ + new Messages::CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ] + ), + Temperature = 1, + Thinking = new Messages::ThinkingConfigEnabled(1024), + ToolChoice = new Messages::ToolChoiceAuto() { DisableParallelToolUse = true }, + Tools = + [ + new Messages::Tool() + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = Messages::TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Messages::Type.Custom, + }, + ], + TopK = 5, + TopP = 0.7, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = Messages::Model.ClaudeOpus4_5_20251101, + }; + + Assert.Null(model.Metadata); + Assert.False(model.RawData.ContainsKey("metadata")); + Assert.Null(model.ServiceTier); + Assert.False(model.RawData.ContainsKey("service_tier")); + Assert.Null(model.StopSequences); + Assert.False(model.RawData.ContainsKey("stop_sequences")); + Assert.Null(model.Stream); + Assert.False(model.RawData.ContainsKey("stream")); + Assert.Null(model.System); + Assert.False(model.RawData.ContainsKey("system")); + Assert.Null(model.Temperature); + Assert.False(model.RawData.ContainsKey("temperature")); + Assert.Null(model.Thinking); + Assert.False(model.RawData.ContainsKey("thinking")); + Assert.Null(model.ToolChoice); + Assert.False(model.RawData.ContainsKey("tool_choice")); + Assert.Null(model.Tools); + Assert.False(model.RawData.ContainsKey("tools")); + Assert.Null(model.TopK); + Assert.False(model.RawData.ContainsKey("top_k")); + Assert.Null(model.TopP); + Assert.False(model.RawData.ContainsKey("top_p")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = Messages::Model.ClaudeOpus4_5_20251101, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = Messages::Model.ClaudeOpus4_5_20251101, + + // Null should be interpreted as omitted for these properties + Metadata = null, + ServiceTier = null, + StopSequences = null, + Stream = null, + System = null, + Temperature = null, + Thinking = null, + ToolChoice = null, + Tools = null, + TopK = null, + TopP = null, + }; + + Assert.Null(model.Metadata); + Assert.False(model.RawData.ContainsKey("metadata")); + Assert.Null(model.ServiceTier); + Assert.False(model.RawData.ContainsKey("service_tier")); + Assert.Null(model.StopSequences); + Assert.False(model.RawData.ContainsKey("stop_sequences")); + Assert.Null(model.Stream); + Assert.False(model.RawData.ContainsKey("stream")); + Assert.Null(model.System); + Assert.False(model.RawData.ContainsKey("system")); + Assert.Null(model.Temperature); + Assert.False(model.RawData.ContainsKey("temperature")); + Assert.Null(model.Thinking); + Assert.False(model.RawData.ContainsKey("thinking")); + Assert.Null(model.ToolChoice); + Assert.False(model.RawData.ContainsKey("tool_choice")); + Assert.Null(model.Tools); + Assert.False(model.RawData.ContainsKey("tools")); + Assert.Null(model.TopK); + Assert.False(model.RawData.ContainsKey("top_k")); + Assert.Null(model.TopP); + Assert.False(model.RawData.ContainsKey("top_p")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new Params + { + MaxTokens = 1024, + Messages = [new() { Content = "Hello, world", Role = Messages::Role.User }], + Model = Messages::Model.ClaudeOpus4_5_20251101, + + // Null should be interpreted as omitted for these properties + Metadata = null, + ServiceTier = null, + StopSequences = null, + Stream = null, + System = null, + Temperature = null, + Thinking = null, + ToolChoice = null, + Tools = null, + TopK = null, + TopP = null, + }; + + model.Validate(); + } +} + +public class ServiceTierTest : TestBase +{ + [Theory] + [InlineData(ServiceTier.Auto)] + [InlineData(ServiceTier.StandardOnly)] + public void Validation_Works(ServiceTier rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(ServiceTier.Auto)] + [InlineData(ServiceTier.StandardOnly)] + public void SerializationRoundtrip_Works(ServiceTier rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/Batches/BatchListPageResponseTest.cs b/src/Anthropic.Tests/Models/Messages/Batches/BatchListPageResponseTest.cs new file mode 100644 index 00000000..4f795f44 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/Batches/BatchListPageResponseTest.cs @@ -0,0 +1,228 @@ +using System; +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Messages.Batches; + +namespace Anthropic.Tests.Models.Messages.Batches; + +public class BatchListPageResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new BatchListPageResponse + { + Data = + [ + new() + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + List expectedData = + [ + new() + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }, + ]; + string expectedFirstID = "first_id"; + bool expectedHasMore = true; + string expectedLastID = "last_id"; + + Assert.Equal(expectedData.Count, model.Data.Count); + for (int i = 0; i < expectedData.Count; i++) + { + Assert.Equal(expectedData[i], model.Data[i]); + } + Assert.Equal(expectedFirstID, model.FirstID); + Assert.Equal(expectedHasMore, model.HasMore); + Assert.Equal(expectedLastID, model.LastID); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new BatchListPageResponse + { + Data = + [ + new() + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new BatchListPageResponse + { + Data = + [ + new() + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedData = + [ + new() + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }, + ]; + string expectedFirstID = "first_id"; + bool expectedHasMore = true; + string expectedLastID = "last_id"; + + Assert.Equal(expectedData.Count, deserialized.Data.Count); + for (int i = 0; i < expectedData.Count; i++) + { + Assert.Equal(expectedData[i], deserialized.Data[i]); + } + Assert.Equal(expectedFirstID, deserialized.FirstID); + Assert.Equal(expectedHasMore, deserialized.HasMore); + Assert.Equal(expectedLastID, deserialized.LastID); + } + + [Fact] + public void Validation_Works() + { + var model = new BatchListPageResponse + { + Data = + [ + new() + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/Batches/DeletedMessageBatchTest.cs b/src/Anthropic.Tests/Models/Messages/Batches/DeletedMessageBatchTest.cs new file mode 100644 index 00000000..81dc7cfe --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/Batches/DeletedMessageBatchTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Messages.Batches; + +namespace Anthropic.Tests.Models.Messages.Batches; + +public class DeletedMessageBatchTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new DeletedMessageBatch { ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF" }; + + string expectedID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"message_batch_deleted\"" + ); + + Assert.Equal(expectedID, model.ID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new DeletedMessageBatch { ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new DeletedMessageBatch { ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"message_batch_deleted\"" + ); + + Assert.Equal(expectedID, deserialized.ID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new DeletedMessageBatch { ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchCanceledResultTest.cs b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchCanceledResultTest.cs new file mode 100644 index 00000000..638201e9 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchCanceledResultTest.cs @@ -0,0 +1,50 @@ +using System.Text.Json; +using Anthropic.Models.Messages.Batches; + +namespace Anthropic.Tests.Models.Messages.Batches; + +public class MessageBatchCanceledResultTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new MessageBatchCanceledResult { }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"canceled\""); + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new MessageBatchCanceledResult { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new MessageBatchCanceledResult { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"canceled\""); + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new MessageBatchCanceledResult { }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchErroredResultTest.cs b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchErroredResultTest.cs new file mode 100644 index 00000000..c83e01cc --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchErroredResultTest.cs @@ -0,0 +1,75 @@ +using System.Text.Json; +using Anthropic.Models; +using Anthropic.Models.Messages.Batches; + +namespace Anthropic.Tests.Models.Messages.Batches; + +public class MessageBatchErroredResultTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new MessageBatchErroredResult + { + Error = new() { Error = new InvalidRequestError("message"), RequestID = "request_id" }, + }; + + ErrorResponse expectedError = new() + { + Error = new InvalidRequestError("message"), + RequestID = "request_id", + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"errored\""); + + Assert.Equal(expectedError, model.Error); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new MessageBatchErroredResult + { + Error = new() { Error = new InvalidRequestError("message"), RequestID = "request_id" }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new MessageBatchErroredResult + { + Error = new() { Error = new InvalidRequestError("message"), RequestID = "request_id" }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ErrorResponse expectedError = new() + { + Error = new InvalidRequestError("message"), + RequestID = "request_id", + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"errored\""); + + Assert.Equal(expectedError, deserialized.Error); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new MessageBatchErroredResult + { + Error = new() { Error = new InvalidRequestError("message"), RequestID = "request_id" }, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchExpiredResultTest.cs b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchExpiredResultTest.cs new file mode 100644 index 00000000..24ebc7f1 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchExpiredResultTest.cs @@ -0,0 +1,50 @@ +using System.Text.Json; +using Anthropic.Models.Messages.Batches; + +namespace Anthropic.Tests.Models.Messages.Batches; + +public class MessageBatchExpiredResultTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new MessageBatchExpiredResult { }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"expired\""); + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new MessageBatchExpiredResult { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new MessageBatchExpiredResult { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"expired\""); + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new MessageBatchExpiredResult { }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchIndividualResponseTest.cs b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchIndividualResponseTest.cs new file mode 100644 index 00000000..2e67376b --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchIndividualResponseTest.cs @@ -0,0 +1,317 @@ +using System.Text.Json; +using Anthropic.Models.Messages; +using Anthropic.Models.Messages.Batches; + +namespace Anthropic.Tests.Models.Messages.Batches; + +public class MessageBatchIndividualResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new MessageBatchIndividualResponse + { + CustomID = "my-custom-id-1", + Result = new MessageBatchSucceededResult( + new Message() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + } + ), + }; + + string expectedCustomID = "my-custom-id-1"; + MessageBatchResult expectedResult = new MessageBatchSucceededResult( + new Message() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + } + ); + + Assert.Equal(expectedCustomID, model.CustomID); + Assert.Equal(expectedResult, model.Result); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new MessageBatchIndividualResponse + { + CustomID = "my-custom-id-1", + Result = new MessageBatchSucceededResult( + new Message() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + } + ), + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new MessageBatchIndividualResponse + { + CustomID = "my-custom-id-1", + Result = new MessageBatchSucceededResult( + new Message() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + } + ), + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCustomID = "my-custom-id-1"; + MessageBatchResult expectedResult = new MessageBatchSucceededResult( + new Message() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + } + ); + + Assert.Equal(expectedCustomID, deserialized.CustomID); + Assert.Equal(expectedResult, deserialized.Result); + } + + [Fact] + public void Validation_Works() + { + var model = new MessageBatchIndividualResponse + { + CustomID = "my-custom-id-1", + Result = new MessageBatchSucceededResult( + new Message() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + } + ), + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchRequestCountsTest.cs b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchRequestCountsTest.cs new file mode 100644 index 00000000..fb46210a --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchRequestCountsTest.cs @@ -0,0 +1,94 @@ +using System.Text.Json; +using Anthropic.Models.Messages.Batches; + +namespace Anthropic.Tests.Models.Messages.Batches; + +public class MessageBatchRequestCountsTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new MessageBatchRequestCounts + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }; + + long expectedCanceled = 10; + long expectedErrored = 30; + long expectedExpired = 10; + long expectedProcessing = 100; + long expectedSucceeded = 50; + + Assert.Equal(expectedCanceled, model.Canceled); + Assert.Equal(expectedErrored, model.Errored); + Assert.Equal(expectedExpired, model.Expired); + Assert.Equal(expectedProcessing, model.Processing); + Assert.Equal(expectedSucceeded, model.Succeeded); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new MessageBatchRequestCounts + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new MessageBatchRequestCounts + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedCanceled = 10; + long expectedErrored = 30; + long expectedExpired = 10; + long expectedProcessing = 100; + long expectedSucceeded = 50; + + Assert.Equal(expectedCanceled, deserialized.Canceled); + Assert.Equal(expectedErrored, deserialized.Errored); + Assert.Equal(expectedExpired, deserialized.Expired); + Assert.Equal(expectedProcessing, deserialized.Processing); + Assert.Equal(expectedSucceeded, deserialized.Succeeded); + } + + [Fact] + public void Validation_Works() + { + var model = new MessageBatchRequestCounts + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchResultTest.cs b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchResultTest.cs new file mode 100644 index 00000000..0cfbec85 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchResultTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Messages.Batches; diff --git a/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchSucceededResultTest.cs b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchSucceededResultTest.cs new file mode 100644 index 00000000..7323dd22 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchSucceededResultTest.cs @@ -0,0 +1,293 @@ +using System.Text.Json; +using Anthropic.Models.Messages; +using Anthropic.Models.Messages.Batches; + +namespace Anthropic.Tests.Models.Messages.Batches; + +public class MessageBatchSucceededResultTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new MessageBatchSucceededResult + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }, + }; + + Message expectedMessage = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"succeeded\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new MessageBatchSucceededResult + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new MessageBatchSucceededResult + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + Message expectedMessage = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"succeeded\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new MessageBatchSucceededResult + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchTest.cs b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchTest.cs new file mode 100644 index 00000000..92155594 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/Batches/MessageBatchTest.cs @@ -0,0 +1,243 @@ +using System; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Messages.Batches; + +namespace Anthropic.Tests.Models.Messages.Batches; + +public class MessageBatchTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new MessageBatch + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }; + + string expectedID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF"; + DateTimeOffset expectedArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + DateTimeOffset expectedCancelInitiatedAt = DateTimeOffset.Parse( + "2024-08-20T18:37:24.100435Z" + ); + DateTimeOffset expectedCreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + DateTimeOffset expectedEndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + DateTimeOffset expectedExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + ApiEnum expectedProcessingStatus = ProcessingStatus.InProgress; + MessageBatchRequestCounts expectedRequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }; + string expectedResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results"; + JsonElement expectedType = JsonSerializer.Deserialize("\"message_batch\""); + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedArchivedAt, model.ArchivedAt); + Assert.Equal(expectedCancelInitiatedAt, model.CancelInitiatedAt); + Assert.Equal(expectedCreatedAt, model.CreatedAt); + Assert.Equal(expectedEndedAt, model.EndedAt); + Assert.Equal(expectedExpiresAt, model.ExpiresAt); + Assert.Equal(expectedProcessingStatus, model.ProcessingStatus); + Assert.Equal(expectedRequestCounts, model.RequestCounts); + Assert.Equal(expectedResultsURL, model.ResultsURL); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new MessageBatch + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new MessageBatch + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF"; + DateTimeOffset expectedArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + DateTimeOffset expectedCancelInitiatedAt = DateTimeOffset.Parse( + "2024-08-20T18:37:24.100435Z" + ); + DateTimeOffset expectedCreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + DateTimeOffset expectedEndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + DateTimeOffset expectedExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"); + ApiEnum expectedProcessingStatus = ProcessingStatus.InProgress; + MessageBatchRequestCounts expectedRequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }; + string expectedResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results"; + JsonElement expectedType = JsonSerializer.Deserialize("\"message_batch\""); + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedArchivedAt, deserialized.ArchivedAt); + Assert.Equal(expectedCancelInitiatedAt, deserialized.CancelInitiatedAt); + Assert.Equal(expectedCreatedAt, deserialized.CreatedAt); + Assert.Equal(expectedEndedAt, deserialized.EndedAt); + Assert.Equal(expectedExpiresAt, deserialized.ExpiresAt); + Assert.Equal(expectedProcessingStatus, deserialized.ProcessingStatus); + Assert.Equal(expectedRequestCounts, deserialized.RequestCounts); + Assert.Equal(expectedResultsURL, deserialized.ResultsURL); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new MessageBatch + { + ID = "msgbatch_013Zva2CMHLNnXjNJJKqJ2EF", + ArchivedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CancelInitiatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + CreatedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + EndedAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ExpiresAt = DateTimeOffset.Parse("2024-08-20T18:37:24.100435Z"), + ProcessingStatus = ProcessingStatus.InProgress, + RequestCounts = new() + { + Canceled = 10, + Errored = 30, + Expired = 10, + Processing = 100, + Succeeded = 50, + }, + ResultsURL = + "https://api.anthropic.com/v1/messages/batches/msgbatch_013Zva2CMHLNnXjNJJKqJ2EF/results", + }; + + model.Validate(); + } +} + +public class ProcessingStatusTest : TestBase +{ + [Theory] + [InlineData(ProcessingStatus.InProgress)] + [InlineData(ProcessingStatus.Canceling)] + [InlineData(ProcessingStatus.Ended)] + public void Validation_Works(ProcessingStatus rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(ProcessingStatus.InProgress)] + [InlineData(ProcessingStatus.Canceling)] + [InlineData(ProcessingStatus.Ended)] + public void SerializationRoundtrip_Works(ProcessingStatus rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/CacheControlEphemeralTest.cs b/src/Anthropic.Tests/Models/Messages/CacheControlEphemeralTest.cs new file mode 100644 index 00000000..3f2af42f --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/CacheControlEphemeralTest.cs @@ -0,0 +1,154 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class CacheControlEphemeralTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new CacheControlEphemeral { TTL = TTL.TTL5m }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"ephemeral\""); + ApiEnum expectedTTL = TTL.TTL5m; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedTTL, model.TTL); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new CacheControlEphemeral { TTL = TTL.TTL5m }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new CacheControlEphemeral { TTL = TTL.TTL5m }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"ephemeral\""); + ApiEnum expectedTTL = TTL.TTL5m; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedTTL, deserialized.TTL); + } + + [Fact] + public void Validation_Works() + { + var model = new CacheControlEphemeral { TTL = TTL.TTL5m }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new CacheControlEphemeral { }; + + Assert.Null(model.TTL); + Assert.False(model.RawData.ContainsKey("ttl")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new CacheControlEphemeral { }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new CacheControlEphemeral + { + // Null should be interpreted as omitted for these properties + TTL = null, + }; + + Assert.Null(model.TTL); + Assert.False(model.RawData.ContainsKey("ttl")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new CacheControlEphemeral + { + // Null should be interpreted as omitted for these properties + TTL = null, + }; + + model.Validate(); + } +} + +public class TTLTest : TestBase +{ + [Theory] + [InlineData(TTL.TTL5m)] + [InlineData(TTL.TTL1h)] + public void Validation_Works(TTL rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(TTL.TTL5m)] + [InlineData(TTL.TTL1h)] + public void SerializationRoundtrip_Works(TTL rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/CacheCreationTest.cs b/src/Anthropic.Tests/Models/Messages/CacheCreationTest.cs new file mode 100644 index 00000000..87544dd5 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/CacheCreationTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class CacheCreationTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new CacheCreation { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }; + + long expectedEphemeral1hInputTokens = 0; + long expectedEphemeral5mInputTokens = 0; + + Assert.Equal(expectedEphemeral1hInputTokens, model.Ephemeral1hInputTokens); + Assert.Equal(expectedEphemeral5mInputTokens, model.Ephemeral5mInputTokens); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new CacheCreation { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new CacheCreation { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedEphemeral1hInputTokens = 0; + long expectedEphemeral5mInputTokens = 0; + + Assert.Equal(expectedEphemeral1hInputTokens, deserialized.Ephemeral1hInputTokens); + Assert.Equal(expectedEphemeral5mInputTokens, deserialized.Ephemeral5mInputTokens); + } + + [Fact] + public void Validation_Works() + { + var model = new CacheCreation { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/CitationCharLocationParamTest.cs b/src/Anthropic.Tests/Models/Messages/CitationCharLocationParamTest.cs new file mode 100644 index 00000000..31106975 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/CitationCharLocationParamTest.cs @@ -0,0 +1,98 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class CitationCharLocationParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new CitationCharLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }; + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "x"; + long expectedEndCharIndex = 0; + long expectedStartCharIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize("\"char_location\""); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedDocumentIndex, model.DocumentIndex); + Assert.Equal(expectedDocumentTitle, model.DocumentTitle); + Assert.Equal(expectedEndCharIndex, model.EndCharIndex); + Assert.Equal(expectedStartCharIndex, model.StartCharIndex); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new CitationCharLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new CitationCharLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "x"; + long expectedEndCharIndex = 0; + long expectedStartCharIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize("\"char_location\""); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedDocumentIndex, deserialized.DocumentIndex); + Assert.Equal(expectedDocumentTitle, deserialized.DocumentTitle); + Assert.Equal(expectedEndCharIndex, deserialized.EndCharIndex); + Assert.Equal(expectedStartCharIndex, deserialized.StartCharIndex); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new CitationCharLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/CitationCharLocationTest.cs b/src/Anthropic.Tests/Models/Messages/CitationCharLocationTest.cs new file mode 100644 index 00000000..292050da --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/CitationCharLocationTest.cs @@ -0,0 +1,106 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class CitationCharLocationTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new CitationCharLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }; + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "document_title"; + long expectedEndCharIndex = 0; + string expectedFileID = "file_id"; + long expectedStartCharIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize("\"char_location\""); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedDocumentIndex, model.DocumentIndex); + Assert.Equal(expectedDocumentTitle, model.DocumentTitle); + Assert.Equal(expectedEndCharIndex, model.EndCharIndex); + Assert.Equal(expectedFileID, model.FileID); + Assert.Equal(expectedStartCharIndex, model.StartCharIndex); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new CitationCharLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new CitationCharLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "document_title"; + long expectedEndCharIndex = 0; + string expectedFileID = "file_id"; + long expectedStartCharIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize("\"char_location\""); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedDocumentIndex, deserialized.DocumentIndex); + Assert.Equal(expectedDocumentTitle, deserialized.DocumentTitle); + Assert.Equal(expectedEndCharIndex, deserialized.EndCharIndex); + Assert.Equal(expectedFileID, deserialized.FileID); + Assert.Equal(expectedStartCharIndex, deserialized.StartCharIndex); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new CitationCharLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/CitationContentBlockLocationParamTest.cs b/src/Anthropic.Tests/Models/Messages/CitationContentBlockLocationParamTest.cs new file mode 100644 index 00000000..87c2da34 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/CitationContentBlockLocationParamTest.cs @@ -0,0 +1,102 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class CitationContentBlockLocationParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new CitationContentBlockLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndBlockIndex = 0, + StartBlockIndex = 0, + }; + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "x"; + long expectedEndBlockIndex = 0; + long expectedStartBlockIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_location\"" + ); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedDocumentIndex, model.DocumentIndex); + Assert.Equal(expectedDocumentTitle, model.DocumentTitle); + Assert.Equal(expectedEndBlockIndex, model.EndBlockIndex); + Assert.Equal(expectedStartBlockIndex, model.StartBlockIndex); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new CitationContentBlockLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndBlockIndex = 0, + StartBlockIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new CitationContentBlockLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndBlockIndex = 0, + StartBlockIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "x"; + long expectedEndBlockIndex = 0; + long expectedStartBlockIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_location\"" + ); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedDocumentIndex, deserialized.DocumentIndex); + Assert.Equal(expectedDocumentTitle, deserialized.DocumentTitle); + Assert.Equal(expectedEndBlockIndex, deserialized.EndBlockIndex); + Assert.Equal(expectedStartBlockIndex, deserialized.StartBlockIndex); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new CitationContentBlockLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndBlockIndex = 0, + StartBlockIndex = 0, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/CitationContentBlockLocationTest.cs b/src/Anthropic.Tests/Models/Messages/CitationContentBlockLocationTest.cs new file mode 100644 index 00000000..39cdaa60 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/CitationContentBlockLocationTest.cs @@ -0,0 +1,110 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class CitationContentBlockLocationTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new CitationContentBlockLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndBlockIndex = 0, + FileID = "file_id", + StartBlockIndex = 0, + }; + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "document_title"; + long expectedEndBlockIndex = 0; + string expectedFileID = "file_id"; + long expectedStartBlockIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_location\"" + ); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedDocumentIndex, model.DocumentIndex); + Assert.Equal(expectedDocumentTitle, model.DocumentTitle); + Assert.Equal(expectedEndBlockIndex, model.EndBlockIndex); + Assert.Equal(expectedFileID, model.FileID); + Assert.Equal(expectedStartBlockIndex, model.StartBlockIndex); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new CitationContentBlockLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndBlockIndex = 0, + FileID = "file_id", + StartBlockIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new CitationContentBlockLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndBlockIndex = 0, + FileID = "file_id", + StartBlockIndex = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "document_title"; + long expectedEndBlockIndex = 0; + string expectedFileID = "file_id"; + long expectedStartBlockIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_location\"" + ); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedDocumentIndex, deserialized.DocumentIndex); + Assert.Equal(expectedDocumentTitle, deserialized.DocumentTitle); + Assert.Equal(expectedEndBlockIndex, deserialized.EndBlockIndex); + Assert.Equal(expectedFileID, deserialized.FileID); + Assert.Equal(expectedStartBlockIndex, deserialized.StartBlockIndex); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new CitationContentBlockLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndBlockIndex = 0, + FileID = "file_id", + StartBlockIndex = 0, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/CitationPageLocationParamTest.cs b/src/Anthropic.Tests/Models/Messages/CitationPageLocationParamTest.cs new file mode 100644 index 00000000..77be9f57 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/CitationPageLocationParamTest.cs @@ -0,0 +1,98 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class CitationPageLocationParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new CitationPageLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndPageNumber = 0, + StartPageNumber = 1, + }; + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "x"; + long expectedEndPageNumber = 0; + long expectedStartPageNumber = 1; + JsonElement expectedType = JsonSerializer.Deserialize("\"page_location\""); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedDocumentIndex, model.DocumentIndex); + Assert.Equal(expectedDocumentTitle, model.DocumentTitle); + Assert.Equal(expectedEndPageNumber, model.EndPageNumber); + Assert.Equal(expectedStartPageNumber, model.StartPageNumber); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new CitationPageLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndPageNumber = 0, + StartPageNumber = 1, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new CitationPageLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndPageNumber = 0, + StartPageNumber = 1, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "x"; + long expectedEndPageNumber = 0; + long expectedStartPageNumber = 1; + JsonElement expectedType = JsonSerializer.Deserialize("\"page_location\""); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedDocumentIndex, deserialized.DocumentIndex); + Assert.Equal(expectedDocumentTitle, deserialized.DocumentTitle); + Assert.Equal(expectedEndPageNumber, deserialized.EndPageNumber); + Assert.Equal(expectedStartPageNumber, deserialized.StartPageNumber); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new CitationPageLocationParam + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndPageNumber = 0, + StartPageNumber = 1, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/CitationPageLocationTest.cs b/src/Anthropic.Tests/Models/Messages/CitationPageLocationTest.cs new file mode 100644 index 00000000..7c2d660d --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/CitationPageLocationTest.cs @@ -0,0 +1,106 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class CitationPageLocationTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new CitationPageLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndPageNumber = 0, + FileID = "file_id", + StartPageNumber = 1, + }; + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "document_title"; + long expectedEndPageNumber = 0; + string expectedFileID = "file_id"; + long expectedStartPageNumber = 1; + JsonElement expectedType = JsonSerializer.Deserialize("\"page_location\""); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedDocumentIndex, model.DocumentIndex); + Assert.Equal(expectedDocumentTitle, model.DocumentTitle); + Assert.Equal(expectedEndPageNumber, model.EndPageNumber); + Assert.Equal(expectedFileID, model.FileID); + Assert.Equal(expectedStartPageNumber, model.StartPageNumber); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new CitationPageLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndPageNumber = 0, + FileID = "file_id", + StartPageNumber = 1, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new CitationPageLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndPageNumber = 0, + FileID = "file_id", + StartPageNumber = 1, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedDocumentIndex = 0; + string expectedDocumentTitle = "document_title"; + long expectedEndPageNumber = 0; + string expectedFileID = "file_id"; + long expectedStartPageNumber = 1; + JsonElement expectedType = JsonSerializer.Deserialize("\"page_location\""); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedDocumentIndex, deserialized.DocumentIndex); + Assert.Equal(expectedDocumentTitle, deserialized.DocumentTitle); + Assert.Equal(expectedEndPageNumber, deserialized.EndPageNumber); + Assert.Equal(expectedFileID, deserialized.FileID); + Assert.Equal(expectedStartPageNumber, deserialized.StartPageNumber); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new CitationPageLocation + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndPageNumber = 0, + FileID = "file_id", + StartPageNumber = 1, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/CitationSearchResultLocationParamTest.cs b/src/Anthropic.Tests/Models/Messages/CitationSearchResultLocationParamTest.cs new file mode 100644 index 00000000..faa1bcdc --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/CitationSearchResultLocationParamTest.cs @@ -0,0 +1,110 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class CitationSearchResultLocationParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new CitationSearchResultLocationParam + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + string expectedCitedText = "cited_text"; + long expectedEndBlockIndex = 0; + long expectedSearchResultIndex = 0; + string expectedSource = "source"; + long expectedStartBlockIndex = 0; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"search_result_location\"" + ); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedEndBlockIndex, model.EndBlockIndex); + Assert.Equal(expectedSearchResultIndex, model.SearchResultIndex); + Assert.Equal(expectedSource, model.Source); + Assert.Equal(expectedStartBlockIndex, model.StartBlockIndex); + Assert.Equal(expectedTitle, model.Title); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new CitationSearchResultLocationParam + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new CitationSearchResultLocationParam + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedEndBlockIndex = 0; + long expectedSearchResultIndex = 0; + string expectedSource = "source"; + long expectedStartBlockIndex = 0; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"search_result_location\"" + ); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedEndBlockIndex, deserialized.EndBlockIndex); + Assert.Equal(expectedSearchResultIndex, deserialized.SearchResultIndex); + Assert.Equal(expectedSource, deserialized.Source); + Assert.Equal(expectedStartBlockIndex, deserialized.StartBlockIndex); + Assert.Equal(expectedTitle, deserialized.Title); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new CitationSearchResultLocationParam + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/CitationWebSearchResultLocationParamTest.cs b/src/Anthropic.Tests/Models/Messages/CitationWebSearchResultLocationParamTest.cs new file mode 100644 index 00000000..11ecc3c0 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/CitationWebSearchResultLocationParamTest.cs @@ -0,0 +1,94 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class CitationWebSearchResultLocationParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new CitationWebSearchResultLocationParam + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "x", + URL = "x", + }; + + string expectedCitedText = "cited_text"; + string expectedEncryptedIndex = "encrypted_index"; + string expectedTitle = "x"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_result_location\"" + ); + string expectedURL = "x"; + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedEncryptedIndex, model.EncryptedIndex); + Assert.Equal(expectedTitle, model.Title); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedURL, model.URL); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new CitationWebSearchResultLocationParam + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "x", + URL = "x", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new CitationWebSearchResultLocationParam + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "x", + URL = "x", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + string expectedEncryptedIndex = "encrypted_index"; + string expectedTitle = "x"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_result_location\"" + ); + string expectedURL = "x"; + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedEncryptedIndex, deserialized.EncryptedIndex); + Assert.Equal(expectedTitle, deserialized.Title); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedURL, deserialized.URL); + } + + [Fact] + public void Validation_Works() + { + var model = new CitationWebSearchResultLocationParam + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "x", + URL = "x", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/CitationsConfigParamTest.cs b/src/Anthropic.Tests/Models/Messages/CitationsConfigParamTest.cs new file mode 100644 index 00000000..7845fc23 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/CitationsConfigParamTest.cs @@ -0,0 +1,92 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class CitationsConfigParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new CitationsConfigParam { Enabled = true }; + + bool expectedEnabled = true; + + Assert.Equal(expectedEnabled, model.Enabled); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new CitationsConfigParam { Enabled = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new CitationsConfigParam { Enabled = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + bool expectedEnabled = true; + + Assert.Equal(expectedEnabled, deserialized.Enabled); + } + + [Fact] + public void Validation_Works() + { + var model = new CitationsConfigParam { Enabled = true }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new CitationsConfigParam { }; + + Assert.Null(model.Enabled); + Assert.False(model.RawData.ContainsKey("enabled")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new CitationsConfigParam { }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new CitationsConfigParam + { + // Null should be interpreted as omitted for these properties + Enabled = null, + }; + + Assert.Null(model.Enabled); + Assert.False(model.RawData.ContainsKey("enabled")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new CitationsConfigParam + { + // Null should be interpreted as omitted for these properties + Enabled = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/CitationsDeltaTest.cs b/src/Anthropic.Tests/Models/Messages/CitationsDeltaTest.cs new file mode 100644 index 00000000..94904819 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/CitationsDeltaTest.cs @@ -0,0 +1,114 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class CitationsDeltaTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new CitationsDelta + { + Citation = new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + }; + + Citation expectedCitation = new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"citations_delta\""); + + Assert.Equal(expectedCitation, model.Citation); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new CitationsDelta + { + Citation = new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new CitationsDelta + { + Citation = new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + Citation expectedCitation = new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"citations_delta\""); + + Assert.Equal(expectedCitation, deserialized.Citation); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new CitationsDelta + { + Citation = new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/CitationsSearchResultLocationTest.cs b/src/Anthropic.Tests/Models/Messages/CitationsSearchResultLocationTest.cs new file mode 100644 index 00000000..c6acb0dc --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/CitationsSearchResultLocationTest.cs @@ -0,0 +1,110 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class CitationsSearchResultLocationTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new CitationsSearchResultLocation + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + string expectedCitedText = "cited_text"; + long expectedEndBlockIndex = 0; + long expectedSearchResultIndex = 0; + string expectedSource = "source"; + long expectedStartBlockIndex = 0; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"search_result_location\"" + ); + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedEndBlockIndex, model.EndBlockIndex); + Assert.Equal(expectedSearchResultIndex, model.SearchResultIndex); + Assert.Equal(expectedSource, model.Source); + Assert.Equal(expectedStartBlockIndex, model.StartBlockIndex); + Assert.Equal(expectedTitle, model.Title); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new CitationsSearchResultLocation + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new CitationsSearchResultLocation + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + long expectedEndBlockIndex = 0; + long expectedSearchResultIndex = 0; + string expectedSource = "source"; + long expectedStartBlockIndex = 0; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"search_result_location\"" + ); + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedEndBlockIndex, deserialized.EndBlockIndex); + Assert.Equal(expectedSearchResultIndex, deserialized.SearchResultIndex); + Assert.Equal(expectedSource, deserialized.Source); + Assert.Equal(expectedStartBlockIndex, deserialized.StartBlockIndex); + Assert.Equal(expectedTitle, deserialized.Title); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new CitationsSearchResultLocation + { + CitedText = "cited_text", + EndBlockIndex = 0, + SearchResultIndex = 0, + Source = "source", + StartBlockIndex = 0, + Title = "title", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/CitationsWebSearchResultLocationTest.cs b/src/Anthropic.Tests/Models/Messages/CitationsWebSearchResultLocationTest.cs new file mode 100644 index 00000000..5beb54bd --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/CitationsWebSearchResultLocationTest.cs @@ -0,0 +1,94 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class CitationsWebSearchResultLocationTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new CitationsWebSearchResultLocation + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "title", + URL = "url", + }; + + string expectedCitedText = "cited_text"; + string expectedEncryptedIndex = "encrypted_index"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_result_location\"" + ); + string expectedURL = "url"; + + Assert.Equal(expectedCitedText, model.CitedText); + Assert.Equal(expectedEncryptedIndex, model.EncryptedIndex); + Assert.Equal(expectedTitle, model.Title); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedURL, model.URL); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new CitationsWebSearchResultLocation + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "title", + URL = "url", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new CitationsWebSearchResultLocation + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "title", + URL = "url", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedCitedText = "cited_text"; + string expectedEncryptedIndex = "encrypted_index"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_result_location\"" + ); + string expectedURL = "url"; + + Assert.Equal(expectedCitedText, deserialized.CitedText); + Assert.Equal(expectedEncryptedIndex, deserialized.EncryptedIndex); + Assert.Equal(expectedTitle, deserialized.Title); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedURL, deserialized.URL); + } + + [Fact] + public void Validation_Works() + { + var model = new CitationsWebSearchResultLocation + { + CitedText = "cited_text", + EncryptedIndex = "encrypted_index", + Title = "title", + URL = "url", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ContentBlockParamTest.cs b/src/Anthropic.Tests/Models/Messages/ContentBlockParamTest.cs new file mode 100644 index 00000000..cec52f06 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ContentBlockParamTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Messages; diff --git a/src/Anthropic.Tests/Models/Messages/ContentBlockSourceContentTest.cs b/src/Anthropic.Tests/Models/Messages/ContentBlockSourceContentTest.cs new file mode 100644 index 00000000..cec52f06 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ContentBlockSourceContentTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Messages; diff --git a/src/Anthropic.Tests/Models/Messages/ContentBlockSourceTest.cs b/src/Anthropic.Tests/Models/Messages/ContentBlockSourceTest.cs new file mode 100644 index 00000000..87f07e8d --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ContentBlockSourceTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ContentBlockSourceTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ContentBlockSource { Content = "string" }; + + Content expectedContent = "string"; + JsonElement expectedType = JsonSerializer.Deserialize("\"content\""); + + Assert.Equal(expectedContent, model.Content); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ContentBlockSource { Content = "string" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ContentBlockSource { Content = "string" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + Content expectedContent = "string"; + JsonElement expectedType = JsonSerializer.Deserialize("\"content\""); + + Assert.Equal(expectedContent, deserialized.Content); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new ContentBlockSource { Content = "string" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ContentBlockTest.cs b/src/Anthropic.Tests/Models/Messages/ContentBlockTest.cs new file mode 100644 index 00000000..cec52f06 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ContentBlockTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Messages; diff --git a/src/Anthropic.Tests/Models/Messages/DocumentBlockParamTest.cs b/src/Anthropic.Tests/Models/Messages/DocumentBlockParamTest.cs new file mode 100644 index 00000000..180f7406 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/DocumentBlockParamTest.cs @@ -0,0 +1,160 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class DocumentBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new DocumentBlockParam + { + Source = new Base64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }; + + Source expectedSource = new Base64PDFSource("U3RhaW5sZXNzIHJvY2tz"); + JsonElement expectedType = JsonSerializer.Deserialize("\"document\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + CitationsConfigParam expectedCitations = new() { Enabled = true }; + string expectedContext = "x"; + string expectedTitle = "x"; + + Assert.Equal(expectedSource, model.Source); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedCitations, model.Citations); + Assert.Equal(expectedContext, model.Context); + Assert.Equal(expectedTitle, model.Title); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new DocumentBlockParam + { + Source = new Base64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new DocumentBlockParam + { + Source = new Base64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + Source expectedSource = new Base64PDFSource("U3RhaW5sZXNzIHJvY2tz"); + JsonElement expectedType = JsonSerializer.Deserialize("\"document\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + CitationsConfigParam expectedCitations = new() { Enabled = true }; + string expectedContext = "x"; + string expectedTitle = "x"; + + Assert.Equal(expectedSource, deserialized.Source); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedCitations, deserialized.Citations); + Assert.Equal(expectedContext, deserialized.Context); + Assert.Equal(expectedTitle, deserialized.Title); + } + + [Fact] + public void Validation_Works() + { + var model = new DocumentBlockParam + { + Source = new Base64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + Context = "x", + Title = "x", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new DocumentBlockParam { Source = new Base64PDFSource("U3RhaW5sZXNzIHJvY2tz") }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Citations); + Assert.False(model.RawData.ContainsKey("citations")); + Assert.Null(model.Context); + Assert.False(model.RawData.ContainsKey("context")); + Assert.Null(model.Title); + Assert.False(model.RawData.ContainsKey("title")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new DocumentBlockParam { Source = new Base64PDFSource("U3RhaW5sZXNzIHJvY2tz") }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new DocumentBlockParam + { + Source = new Base64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + + CacheControl = null, + Citations = null, + Context = null, + Title = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Citations); + Assert.True(model.RawData.ContainsKey("citations")); + Assert.Null(model.Context); + Assert.True(model.RawData.ContainsKey("context")); + Assert.Null(model.Title); + Assert.True(model.RawData.ContainsKey("title")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new DocumentBlockParam + { + Source = new Base64PDFSource("U3RhaW5sZXNzIHJvY2tz"), + + CacheControl = null, + Citations = null, + Context = null, + Title = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ImageBlockParamTest.cs b/src/Anthropic.Tests/Models/Messages/ImageBlockParamTest.cs new file mode 100644 index 00000000..79b99157 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ImageBlockParamTest.cs @@ -0,0 +1,164 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ImageBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ImageBlockParam + { + Source = new Base64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + ImageBlockParamSource expectedSource = new Base64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"image\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedSource, model.Source); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ImageBlockParam + { + Source = new Base64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ImageBlockParam + { + Source = new Base64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ImageBlockParamSource expectedSource = new Base64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"image\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedSource, deserialized.Source); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new ImageBlockParam + { + Source = new Base64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new ImageBlockParam + { + Source = new Base64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new ImageBlockParam + { + Source = new Base64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new ImageBlockParam + { + Source = new Base64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new ImageBlockParam + { + Source = new Base64ImageSource() + { + Data = "U3RhaW5sZXNzIHJvY2tz", + MediaType = MediaType.ImageJPEG, + }, + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/InputJSONDeltaTest.cs b/src/Anthropic.Tests/Models/Messages/InputJSONDeltaTest.cs new file mode 100644 index 00000000..2d8e21a1 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/InputJSONDeltaTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class InputJSONDeltaTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new InputJSONDelta { PartialJSON = "partial_json" }; + + string expectedPartialJSON = "partial_json"; + JsonElement expectedType = JsonSerializer.Deserialize("\"input_json_delta\""); + + Assert.Equal(expectedPartialJSON, model.PartialJSON); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new InputJSONDelta { PartialJSON = "partial_json" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new InputJSONDelta { PartialJSON = "partial_json" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedPartialJSON = "partial_json"; + JsonElement expectedType = JsonSerializer.Deserialize("\"input_json_delta\""); + + Assert.Equal(expectedPartialJSON, deserialized.PartialJSON); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new InputJSONDelta { PartialJSON = "partial_json" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/MessageCountTokensParamsTest.cs b/src/Anthropic.Tests/Models/Messages/MessageCountTokensParamsTest.cs new file mode 100644 index 00000000..cec52f06 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/MessageCountTokensParamsTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Messages; diff --git a/src/Anthropic.Tests/Models/Messages/MessageCountTokensToolTest.cs b/src/Anthropic.Tests/Models/Messages/MessageCountTokensToolTest.cs new file mode 100644 index 00000000..cec52f06 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/MessageCountTokensToolTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Messages; diff --git a/src/Anthropic.Tests/Models/Messages/MessageCreateParamsTest.cs b/src/Anthropic.Tests/Models/Messages/MessageCreateParamsTest.cs new file mode 100644 index 00000000..16cbe419 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/MessageCreateParamsTest.cs @@ -0,0 +1,62 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ServiceTierTest : TestBase +{ + [Theory] + [InlineData(ServiceTier.Auto)] + [InlineData(ServiceTier.StandardOnly)] + public void Validation_Works(ServiceTier rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(ServiceTier.Auto)] + [InlineData(ServiceTier.StandardOnly)] + public void SerializationRoundtrip_Works(ServiceTier rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/MessageDeltaUsageTest.cs b/src/Anthropic.Tests/Models/Messages/MessageDeltaUsageTest.cs new file mode 100644 index 00000000..80e77001 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/MessageDeltaUsageTest.cs @@ -0,0 +1,94 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class MessageDeltaUsageTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new MessageDeltaUsage + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + }; + + long expectedCacheCreationInputTokens = 2051; + long expectedCacheReadInputTokens = 2051; + long expectedInputTokens = 2095; + long expectedOutputTokens = 503; + ServerToolUsage expectedServerToolUse = new(0); + + Assert.Equal(expectedCacheCreationInputTokens, model.CacheCreationInputTokens); + Assert.Equal(expectedCacheReadInputTokens, model.CacheReadInputTokens); + Assert.Equal(expectedInputTokens, model.InputTokens); + Assert.Equal(expectedOutputTokens, model.OutputTokens); + Assert.Equal(expectedServerToolUse, model.ServerToolUse); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new MessageDeltaUsage + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new MessageDeltaUsage + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedCacheCreationInputTokens = 2051; + long expectedCacheReadInputTokens = 2051; + long expectedInputTokens = 2095; + long expectedOutputTokens = 503; + ServerToolUsage expectedServerToolUse = new(0); + + Assert.Equal(expectedCacheCreationInputTokens, deserialized.CacheCreationInputTokens); + Assert.Equal(expectedCacheReadInputTokens, deserialized.CacheReadInputTokens); + Assert.Equal(expectedInputTokens, deserialized.InputTokens); + Assert.Equal(expectedOutputTokens, deserialized.OutputTokens); + Assert.Equal(expectedServerToolUse, deserialized.ServerToolUse); + } + + [Fact] + public void Validation_Works() + { + var model = new MessageDeltaUsage + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/MessageParamTest.cs b/src/Anthropic.Tests/Models/Messages/MessageParamTest.cs new file mode 100644 index 00000000..0ab2e2b7 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/MessageParamTest.cs @@ -0,0 +1,112 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class MessageParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new MessageParam { Content = "string", Role = Role.User }; + + MessageParamContent expectedContent = "string"; + ApiEnum expectedRole = Role.User; + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedRole, model.Role); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new MessageParam { Content = "string", Role = Role.User }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new MessageParam { Content = "string", Role = Role.User }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + MessageParamContent expectedContent = "string"; + ApiEnum expectedRole = Role.User; + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedRole, deserialized.Role); + } + + [Fact] + public void Validation_Works() + { + var model = new MessageParam { Content = "string", Role = Role.User }; + + model.Validate(); + } +} + +public class RoleTest : TestBase +{ + [Theory] + [InlineData(Role.User)] + [InlineData(Role.Assistant)] + public void Validation_Works(Role rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(Role.User)] + [InlineData(Role.Assistant)] + public void SerializationRoundtrip_Works(Role rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/MessageTest.cs b/src/Anthropic.Tests/Models/Messages/MessageTest.cs new file mode 100644 index 00000000..dd3c4fbe --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/MessageTest.cs @@ -0,0 +1,282 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class MessageTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Message + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }; + + string expectedID = "msg_013Zva2CMHLNnXjNJJKqJ2EF"; + List expectedContent = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ]; + ApiEnum expectedModel = Model.ClaudeOpus4_5_20251101; + JsonElement expectedRole = JsonSerializer.Deserialize("\"assistant\""); + ApiEnum expectedStopReason = StopReason.EndTurn; + string expectedStopSequence = null; + JsonElement expectedType = JsonSerializer.Deserialize("\"message\""); + Usage expectedUsage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedContent.Count, model.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], model.Content[i]); + } + Assert.Equal(expectedModel, model.Model); + Assert.True(JsonElement.DeepEquals(expectedRole, model.Role)); + Assert.Equal(expectedStopReason, model.StopReason); + Assert.Equal(expectedStopSequence, model.StopSequence); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedUsage, model.Usage); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Message + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Message + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "msg_013Zva2CMHLNnXjNJJKqJ2EF"; + List expectedContent = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ]; + ApiEnum expectedModel = Model.ClaudeOpus4_5_20251101; + JsonElement expectedRole = JsonSerializer.Deserialize("\"assistant\""); + ApiEnum expectedStopReason = StopReason.EndTurn; + string expectedStopSequence = null; + JsonElement expectedType = JsonSerializer.Deserialize("\"message\""); + Usage expectedUsage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedContent.Count, deserialized.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], deserialized.Content[i]); + } + Assert.Equal(expectedModel, deserialized.Model); + Assert.True(JsonElement.DeepEquals(expectedRole, deserialized.Role)); + Assert.Equal(expectedStopReason, deserialized.StopReason); + Assert.Equal(expectedStopSequence, deserialized.StopSequence); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedUsage, deserialized.Usage); + } + + [Fact] + public void Validation_Works() + { + var model = new Message + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/MessageTokensCountTest.cs b/src/Anthropic.Tests/Models/Messages/MessageTokensCountTest.cs new file mode 100644 index 00000000..f335e9dd --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/MessageTokensCountTest.cs @@ -0,0 +1,50 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class MessageTokensCountTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new MessageTokensCount { InputTokens = 2095 }; + + long expectedInputTokens = 2095; + + Assert.Equal(expectedInputTokens, model.InputTokens); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new MessageTokensCount { InputTokens = 2095 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new MessageTokensCount { InputTokens = 2095 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedInputTokens = 2095; + + Assert.Equal(expectedInputTokens, deserialized.InputTokens); + } + + [Fact] + public void Validation_Works() + { + var model = new MessageTokensCount { InputTokens = 2095 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/MetadataTest.cs b/src/Anthropic.Tests/Models/Messages/MetadataTest.cs new file mode 100644 index 00000000..3e39849e --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/MetadataTest.cs @@ -0,0 +1,84 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class MetadataTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Metadata { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }; + + string expectedUserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b"; + + Assert.Equal(expectedUserID, model.UserID); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Metadata { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Metadata { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedUserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b"; + + Assert.Equal(expectedUserID, deserialized.UserID); + } + + [Fact] + public void Validation_Works() + { + var model = new Metadata { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new Metadata { }; + + Assert.Null(model.UserID); + Assert.False(model.RawData.ContainsKey("user_id")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new Metadata { }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new Metadata { UserID = null }; + + Assert.Null(model.UserID); + Assert.True(model.RawData.ContainsKey("user_id")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new Metadata { UserID = null }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ModelTest.cs b/src/Anthropic.Tests/Models/Messages/ModelTest.cs new file mode 100644 index 00000000..9e40df5b --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ModelTest.cs @@ -0,0 +1,98 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ModelTest : TestBase +{ + [Theory] + [InlineData(Model.ClaudeOpus4_5_20251101)] + [InlineData(Model.ClaudeOpus4_5)] + [InlineData(Model.Claude3_7SonnetLatest)] + [InlineData(Model.Claude3_7Sonnet20250219)] + [InlineData(Model.Claude3_5HaikuLatest)] + [InlineData(Model.Claude3_5Haiku20241022)] + [InlineData(Model.ClaudeHaiku4_5)] + [InlineData(Model.ClaudeHaiku4_5_20251001)] + [InlineData(Model.ClaudeSonnet4_20250514)] + [InlineData(Model.ClaudeSonnet4_0)] + [InlineData(Model.Claude4Sonnet20250514)] + [InlineData(Model.ClaudeSonnet4_5)] + [InlineData(Model.ClaudeSonnet4_5_20250929)] + [InlineData(Model.ClaudeOpus4_0)] + [InlineData(Model.ClaudeOpus4_20250514)] + [InlineData(Model.Claude4Opus20250514)] + [InlineData(Model.ClaudeOpus4_1_20250805)] + [InlineData(Model.Claude3OpusLatest)] + [InlineData(Model.Claude_3_Opus_20240229)] + [InlineData(Model.Claude_3_Haiku_20240307)] + public void Validation_Works(Model rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(Model.ClaudeOpus4_5_20251101)] + [InlineData(Model.ClaudeOpus4_5)] + [InlineData(Model.Claude3_7SonnetLatest)] + [InlineData(Model.Claude3_7Sonnet20250219)] + [InlineData(Model.Claude3_5HaikuLatest)] + [InlineData(Model.Claude3_5Haiku20241022)] + [InlineData(Model.ClaudeHaiku4_5)] + [InlineData(Model.ClaudeHaiku4_5_20251001)] + [InlineData(Model.ClaudeSonnet4_20250514)] + [InlineData(Model.ClaudeSonnet4_0)] + [InlineData(Model.Claude4Sonnet20250514)] + [InlineData(Model.ClaudeSonnet4_5)] + [InlineData(Model.ClaudeSonnet4_5_20250929)] + [InlineData(Model.ClaudeOpus4_0)] + [InlineData(Model.ClaudeOpus4_20250514)] + [InlineData(Model.Claude4Opus20250514)] + [InlineData(Model.ClaudeOpus4_1_20250805)] + [InlineData(Model.Claude3OpusLatest)] + [InlineData(Model.Claude_3_Opus_20240229)] + [InlineData(Model.Claude_3_Haiku_20240307)] + public void SerializationRoundtrip_Works(Model rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/PlainTextSourceTest.cs b/src/Anthropic.Tests/Models/Messages/PlainTextSourceTest.cs new file mode 100644 index 00000000..ad1e69b4 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/PlainTextSourceTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class PlainTextSourceTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new PlainTextSource { Data = "data" }; + + string expectedData = "data"; + JsonElement expectedMediaType = JsonSerializer.Deserialize("\"text/plain\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"text\""); + + Assert.Equal(expectedData, model.Data); + Assert.True(JsonElement.DeepEquals(expectedMediaType, model.MediaType)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new PlainTextSource { Data = "data" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new PlainTextSource { Data = "data" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedData = "data"; + JsonElement expectedMediaType = JsonSerializer.Deserialize("\"text/plain\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"text\""); + + Assert.Equal(expectedData, deserialized.Data); + Assert.True(JsonElement.DeepEquals(expectedMediaType, deserialized.MediaType)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new PlainTextSource { Data = "data" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/RawContentBlockDeltaEventTest.cs b/src/Anthropic.Tests/Models/Messages/RawContentBlockDeltaEventTest.cs new file mode 100644 index 00000000..363e9c5b --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/RawContentBlockDeltaEventTest.cs @@ -0,0 +1,62 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class RawContentBlockDeltaEventTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new RawContentBlockDeltaEvent { Delta = new TextDelta("text"), Index = 0 }; + + RawContentBlockDelta expectedDelta = new TextDelta("text"); + long expectedIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_delta\"" + ); + + Assert.Equal(expectedDelta, model.Delta); + Assert.Equal(expectedIndex, model.Index); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new RawContentBlockDeltaEvent { Delta = new TextDelta("text"), Index = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new RawContentBlockDeltaEvent { Delta = new TextDelta("text"), Index = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + RawContentBlockDelta expectedDelta = new TextDelta("text"); + long expectedIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_delta\"" + ); + + Assert.Equal(expectedDelta, deserialized.Delta); + Assert.Equal(expectedIndex, deserialized.Index); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new RawContentBlockDeltaEvent { Delta = new TextDelta("text"), Index = 0 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/RawContentBlockDeltaTest.cs b/src/Anthropic.Tests/Models/Messages/RawContentBlockDeltaTest.cs new file mode 100644 index 00000000..cec52f06 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/RawContentBlockDeltaTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Messages; diff --git a/src/Anthropic.Tests/Models/Messages/RawContentBlockStartEventTest.cs b/src/Anthropic.Tests/Models/Messages/RawContentBlockStartEventTest.cs new file mode 100644 index 00000000..a9f26c3a --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/RawContentBlockStartEventTest.cs @@ -0,0 +1,168 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class RawContentBlockStartEventTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new RawContentBlockStartEvent + { + ContentBlock = new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }, + Index = 0, + }; + + RawContentBlockStartEventContentBlock expectedContentBlock = new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }; + long expectedIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_start\"" + ); + + Assert.Equal(expectedContentBlock, model.ContentBlock); + Assert.Equal(expectedIndex, model.Index); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new RawContentBlockStartEvent + { + ContentBlock = new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }, + Index = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new RawContentBlockStartEvent + { + ContentBlock = new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }, + Index = 0, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + RawContentBlockStartEventContentBlock expectedContentBlock = new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }; + long expectedIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_start\"" + ); + + Assert.Equal(expectedContentBlock, deserialized.ContentBlock); + Assert.Equal(expectedIndex, deserialized.Index); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new RawContentBlockStartEvent + { + ContentBlock = new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }, + Index = 0, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/RawContentBlockStopEventTest.cs b/src/Anthropic.Tests/Models/Messages/RawContentBlockStopEventTest.cs new file mode 100644 index 00000000..72955901 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/RawContentBlockStopEventTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class RawContentBlockStopEventTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new RawContentBlockStopEvent { Index = 0 }; + + long expectedIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_stop\"" + ); + + Assert.Equal(expectedIndex, model.Index); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new RawContentBlockStopEvent { Index = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new RawContentBlockStopEvent { Index = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedIndex = 0; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"content_block_stop\"" + ); + + Assert.Equal(expectedIndex, deserialized.Index); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new RawContentBlockStopEvent { Index = 0 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/RawMessageDeltaEventTest.cs b/src/Anthropic.Tests/Models/Messages/RawMessageDeltaEventTest.cs new file mode 100644 index 00000000..52019502 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/RawMessageDeltaEventTest.cs @@ -0,0 +1,175 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class RawMessageDeltaEventTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new RawMessageDeltaEvent + { + Delta = new() { StopReason = StopReason.EndTurn, StopSequence = "stop_sequence" }, + Usage = new() + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + }, + }; + + Delta expectedDelta = new() + { + StopReason = StopReason.EndTurn, + StopSequence = "stop_sequence", + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"message_delta\""); + MessageDeltaUsage expectedUsage = new() + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + }; + + Assert.Equal(expectedDelta, model.Delta); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedUsage, model.Usage); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new RawMessageDeltaEvent + { + Delta = new() { StopReason = StopReason.EndTurn, StopSequence = "stop_sequence" }, + Usage = new() + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new RawMessageDeltaEvent + { + Delta = new() { StopReason = StopReason.EndTurn, StopSequence = "stop_sequence" }, + Usage = new() + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + Delta expectedDelta = new() + { + StopReason = StopReason.EndTurn, + StopSequence = "stop_sequence", + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"message_delta\""); + MessageDeltaUsage expectedUsage = new() + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + }; + + Assert.Equal(expectedDelta, deserialized.Delta); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedUsage, deserialized.Usage); + } + + [Fact] + public void Validation_Works() + { + var model = new RawMessageDeltaEvent + { + Delta = new() { StopReason = StopReason.EndTurn, StopSequence = "stop_sequence" }, + Usage = new() + { + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + }, + }; + + model.Validate(); + } +} + +public class DeltaTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Delta { StopReason = StopReason.EndTurn, StopSequence = "stop_sequence" }; + + ApiEnum expectedStopReason = StopReason.EndTurn; + string expectedStopSequence = "stop_sequence"; + + Assert.Equal(expectedStopReason, model.StopReason); + Assert.Equal(expectedStopSequence, model.StopSequence); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Delta { StopReason = StopReason.EndTurn, StopSequence = "stop_sequence" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Delta { StopReason = StopReason.EndTurn, StopSequence = "stop_sequence" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ApiEnum expectedStopReason = StopReason.EndTurn; + string expectedStopSequence = "stop_sequence"; + + Assert.Equal(expectedStopReason, deserialized.StopReason); + Assert.Equal(expectedStopSequence, deserialized.StopSequence); + } + + [Fact] + public void Validation_Works() + { + var model = new Delta { StopReason = StopReason.EndTurn, StopSequence = "stop_sequence" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/RawMessageStartEventTest.cs b/src/Anthropic.Tests/Models/Messages/RawMessageStartEventTest.cs new file mode 100644 index 00000000..03a931fe --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/RawMessageStartEventTest.cs @@ -0,0 +1,292 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class RawMessageStartEventTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new RawMessageStartEvent + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }, + }; + + Message expectedMessage = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"message_start\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new RawMessageStartEvent + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new RawMessageStartEvent + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + Message expectedMessage = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }; + JsonElement expectedType = JsonSerializer.Deserialize("\"message_start\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new RawMessageStartEvent + { + Message = new() + { + ID = "msg_013Zva2CMHLNnXjNJJKqJ2EF", + Content = + [ + new TextBlock() + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "Hi! My name is Claude.", + }, + ], + Model = Model.ClaudeOpus4_5_20251101, + StopReason = StopReason.EndTurn, + StopSequence = null, + Usage = new() + { + CacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }, + }, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/RawMessageStopEventTest.cs b/src/Anthropic.Tests/Models/Messages/RawMessageStopEventTest.cs new file mode 100644 index 00000000..1337d477 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/RawMessageStopEventTest.cs @@ -0,0 +1,50 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class RawMessageStopEventTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new RawMessageStopEvent { }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"message_stop\""); + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new RawMessageStopEvent { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new RawMessageStopEvent { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"message_stop\""); + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new RawMessageStopEvent { }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/RawMessageStreamEventTest.cs b/src/Anthropic.Tests/Models/Messages/RawMessageStreamEventTest.cs new file mode 100644 index 00000000..cec52f06 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/RawMessageStreamEventTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Messages; diff --git a/src/Anthropic.Tests/Models/Messages/RedactedThinkingBlockParamTest.cs b/src/Anthropic.Tests/Models/Messages/RedactedThinkingBlockParamTest.cs new file mode 100644 index 00000000..1d72f734 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/RedactedThinkingBlockParamTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class RedactedThinkingBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new RedactedThinkingBlockParam { Data = "data" }; + + string expectedData = "data"; + JsonElement expectedType = JsonSerializer.Deserialize("\"redacted_thinking\""); + + Assert.Equal(expectedData, model.Data); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new RedactedThinkingBlockParam { Data = "data" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new RedactedThinkingBlockParam { Data = "data" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedData = "data"; + JsonElement expectedType = JsonSerializer.Deserialize("\"redacted_thinking\""); + + Assert.Equal(expectedData, deserialized.Data); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new RedactedThinkingBlockParam { Data = "data" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/RedactedThinkingBlockTest.cs b/src/Anthropic.Tests/Models/Messages/RedactedThinkingBlockTest.cs new file mode 100644 index 00000000..7cbff235 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/RedactedThinkingBlockTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class RedactedThinkingBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new RedactedThinkingBlock { Data = "data" }; + + string expectedData = "data"; + JsonElement expectedType = JsonSerializer.Deserialize("\"redacted_thinking\""); + + Assert.Equal(expectedData, model.Data); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new RedactedThinkingBlock { Data = "data" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new RedactedThinkingBlock { Data = "data" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedData = "data"; + JsonElement expectedType = JsonSerializer.Deserialize("\"redacted_thinking\""); + + Assert.Equal(expectedData, deserialized.Data); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new RedactedThinkingBlock { Data = "data" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/SearchResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Messages/SearchResultBlockParamTest.cs new file mode 100644 index 00000000..7f28f14b --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/SearchResultBlockParamTest.cs @@ -0,0 +1,485 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class SearchResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new SearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + }; + + List expectedContent = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ]; + string expectedSource = "source"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize("\"search_result\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + CitationsConfigParam expectedCitations = new() { Enabled = true }; + + Assert.Equal(expectedContent.Count, model.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], model.Content[i]); + } + Assert.Equal(expectedSource, model.Source); + Assert.Equal(expectedTitle, model.Title); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedCitations, model.Citations); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new SearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new SearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedContent = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ]; + string expectedSource = "source"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize("\"search_result\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + CitationsConfigParam expectedCitations = new() { Enabled = true }; + + Assert.Equal(expectedContent.Count, deserialized.Content.Count); + for (int i = 0; i < expectedContent.Count; i++) + { + Assert.Equal(expectedContent[i], deserialized.Content[i]); + } + Assert.Equal(expectedSource, deserialized.Source); + Assert.Equal(expectedTitle, deserialized.Title); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedCitations, deserialized.Citations); + } + + [Fact] + public void Validation_Works() + { + var model = new SearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = new() { Enabled = true }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new SearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + Assert.Null(model.Citations); + Assert.False(model.RawData.ContainsKey("citations")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new SearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new SearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + Citations = null, + }; + + Assert.Null(model.Citations); + Assert.False(model.RawData.ContainsKey("citations")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new SearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + Citations = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new SearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + Citations = new() { Enabled = true }, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new SearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + Citations = new() { Enabled = true }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new SearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + Citations = new() { Enabled = true }, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new SearchResultBlockParam + { + Content = + [ + new() + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }, + ], + Source = "source", + Title = "title", + Citations = new() { Enabled = true }, + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ServerToolUsageTest.cs b/src/Anthropic.Tests/Models/Messages/ServerToolUsageTest.cs new file mode 100644 index 00000000..28a76102 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ServerToolUsageTest.cs @@ -0,0 +1,50 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ServerToolUsageTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ServerToolUsage { WebSearchRequests = 0 }; + + long expectedWebSearchRequests = 0; + + Assert.Equal(expectedWebSearchRequests, model.WebSearchRequests); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ServerToolUsage { WebSearchRequests = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ServerToolUsage { WebSearchRequests = 0 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedWebSearchRequests = 0; + + Assert.Equal(expectedWebSearchRequests, deserialized.WebSearchRequests); + } + + [Fact] + public void Validation_Works() + { + var model = new ServerToolUsage { WebSearchRequests = 0 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ServerToolUseBlockParamTest.cs b/src/Anthropic.Tests/Models/Messages/ServerToolUseBlockParamTest.cs new file mode 100644 index 00000000..79114b9d --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ServerToolUseBlockParamTest.cs @@ -0,0 +1,183 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ServerToolUseBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string expectedID = "srvtoolu_SQfNkl1n_JR_"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + JsonElement expectedName = JsonSerializer.Deserialize("\"web_search\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"server_tool_use\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedInput.Count, model.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(model.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.Input[item.Key])); + } + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "srvtoolu_SQfNkl1n_JR_"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + JsonElement expectedName = JsonSerializer.Deserialize("\"web_search\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"server_tool_use\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedInput.Count, deserialized.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(deserialized.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.Input[item.Key])); + } + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new ServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new ServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new ServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new ServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new ServerToolUseBlockParam + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ServerToolUseBlockTest.cs b/src/Anthropic.Tests/Models/Messages/ServerToolUseBlockTest.cs new file mode 100644 index 00000000..d752f0fa --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ServerToolUseBlockTest.cs @@ -0,0 +1,109 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ServerToolUseBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ServerToolUseBlock + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }; + + string expectedID = "srvtoolu_SQfNkl1n_JR_"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + JsonElement expectedName = JsonSerializer.Deserialize("\"web_search\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"server_tool_use\""); + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedInput.Count, model.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(model.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.Input[item.Key])); + } + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ServerToolUseBlock + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ServerToolUseBlock + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "srvtoolu_SQfNkl1n_JR_"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + JsonElement expectedName = JsonSerializer.Deserialize("\"web_search\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"server_tool_use\""); + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedInput.Count, deserialized.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(deserialized.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.Input[item.Key])); + } + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new ServerToolUseBlock + { + ID = "srvtoolu_SQfNkl1n_JR_", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/SignatureDeltaTest.cs b/src/Anthropic.Tests/Models/Messages/SignatureDeltaTest.cs new file mode 100644 index 00000000..f8db38c8 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/SignatureDeltaTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class SignatureDeltaTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new SignatureDelta { Signature = "signature" }; + + string expectedSignature = "signature"; + JsonElement expectedType = JsonSerializer.Deserialize("\"signature_delta\""); + + Assert.Equal(expectedSignature, model.Signature); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new SignatureDelta { Signature = "signature" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new SignatureDelta { Signature = "signature" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedSignature = "signature"; + JsonElement expectedType = JsonSerializer.Deserialize("\"signature_delta\""); + + Assert.Equal(expectedSignature, deserialized.Signature); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new SignatureDelta { Signature = "signature" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/StopReasonTest.cs b/src/Anthropic.Tests/Models/Messages/StopReasonTest.cs new file mode 100644 index 00000000..048fcfe2 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/StopReasonTest.cs @@ -0,0 +1,70 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class StopReasonTest : TestBase +{ + [Theory] + [InlineData(StopReason.EndTurn)] + [InlineData(StopReason.MaxTokens)] + [InlineData(StopReason.StopSequence)] + [InlineData(StopReason.ToolUse)] + [InlineData(StopReason.PauseTurn)] + [InlineData(StopReason.Refusal)] + public void Validation_Works(StopReason rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(StopReason.EndTurn)] + [InlineData(StopReason.MaxTokens)] + [InlineData(StopReason.StopSequence)] + [InlineData(StopReason.ToolUse)] + [InlineData(StopReason.PauseTurn)] + [InlineData(StopReason.Refusal)] + public void SerializationRoundtrip_Works(StopReason rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/TextBlockParamTest.cs b/src/Anthropic.Tests/Models/Messages/TextBlockParamTest.cs new file mode 100644 index 00000000..51fd64ef --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/TextBlockParamTest.cs @@ -0,0 +1,201 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class TextBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new TextBlockParam + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }; + + string expectedText = "x"; + JsonElement expectedType = JsonSerializer.Deserialize("\"text\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + List expectedCitations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ]; + + Assert.Equal(expectedText, model.Text); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedCitations.Count, model.Citations.Count); + for (int i = 0; i < expectedCitations.Count; i++) + { + Assert.Equal(expectedCitations[i], model.Citations[i]); + } + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new TextBlockParam + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new TextBlockParam + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedText = "x"; + JsonElement expectedType = JsonSerializer.Deserialize("\"text\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + List expectedCitations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ]; + + Assert.Equal(expectedText, deserialized.Text); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedCitations.Count, deserialized.Citations.Count); + for (int i = 0; i < expectedCitations.Count; i++) + { + Assert.Equal(expectedCitations[i], deserialized.Citations[i]); + } + } + + [Fact] + public void Validation_Works() + { + var model = new TextBlockParam + { + Text = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + Citations = + [ + new CitationCharLocationParam() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "x", + EndCharIndex = 0, + StartCharIndex = 0, + }, + ], + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new TextBlockParam { Text = "x" }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Citations); + Assert.False(model.RawData.ContainsKey("citations")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new TextBlockParam { Text = "x" }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new TextBlockParam + { + Text = "x", + + CacheControl = null, + Citations = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Citations); + Assert.True(model.RawData.ContainsKey("citations")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new TextBlockParam + { + Text = "x", + + CacheControl = null, + Citations = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/TextBlockTest.cs b/src/Anthropic.Tests/Models/Messages/TextBlockTest.cs new file mode 100644 index 00000000..19e7cef4 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/TextBlockTest.cs @@ -0,0 +1,149 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class TextBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new TextBlock + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }; + + List expectedCitations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ]; + string expectedText = "text"; + JsonElement expectedType = JsonSerializer.Deserialize("\"text\""); + + Assert.Equal(expectedCitations.Count, model.Citations.Count); + for (int i = 0; i < expectedCitations.Count; i++) + { + Assert.Equal(expectedCitations[i], model.Citations[i]); + } + Assert.Equal(expectedText, model.Text); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new TextBlock + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new TextBlock + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedCitations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ]; + string expectedText = "text"; + JsonElement expectedType = JsonSerializer.Deserialize("\"text\""); + + Assert.Equal(expectedCitations.Count, deserialized.Citations.Count); + for (int i = 0; i < expectedCitations.Count; i++) + { + Assert.Equal(expectedCitations[i], deserialized.Citations[i]); + } + Assert.Equal(expectedText, deserialized.Text); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new TextBlock + { + Citations = + [ + new CitationCharLocation() + { + CitedText = "cited_text", + DocumentIndex = 0, + DocumentTitle = "document_title", + EndCharIndex = 0, + FileID = "file_id", + StartCharIndex = 0, + }, + ], + Text = "text", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/TextCitationParamTest.cs b/src/Anthropic.Tests/Models/Messages/TextCitationParamTest.cs new file mode 100644 index 00000000..cec52f06 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/TextCitationParamTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Messages; diff --git a/src/Anthropic.Tests/Models/Messages/TextCitationTest.cs b/src/Anthropic.Tests/Models/Messages/TextCitationTest.cs new file mode 100644 index 00000000..cec52f06 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/TextCitationTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Messages; diff --git a/src/Anthropic.Tests/Models/Messages/TextDeltaTest.cs b/src/Anthropic.Tests/Models/Messages/TextDeltaTest.cs new file mode 100644 index 00000000..4898c898 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/TextDeltaTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class TextDeltaTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new TextDelta { Text = "text" }; + + string expectedText = "text"; + JsonElement expectedType = JsonSerializer.Deserialize("\"text_delta\""); + + Assert.Equal(expectedText, model.Text); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new TextDelta { Text = "text" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new TextDelta { Text = "text" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedText = "text"; + JsonElement expectedType = JsonSerializer.Deserialize("\"text_delta\""); + + Assert.Equal(expectedText, deserialized.Text); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new TextDelta { Text = "text" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ThinkingBlockParamTest.cs b/src/Anthropic.Tests/Models/Messages/ThinkingBlockParamTest.cs new file mode 100644 index 00000000..84ca6706 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ThinkingBlockParamTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ThinkingBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ThinkingBlockParam { Signature = "signature", Thinking = "thinking" }; + + string expectedSignature = "signature"; + string expectedThinking = "thinking"; + JsonElement expectedType = JsonSerializer.Deserialize("\"thinking\""); + + Assert.Equal(expectedSignature, model.Signature); + Assert.Equal(expectedThinking, model.Thinking); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ThinkingBlockParam { Signature = "signature", Thinking = "thinking" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ThinkingBlockParam { Signature = "signature", Thinking = "thinking" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedSignature = "signature"; + string expectedThinking = "thinking"; + JsonElement expectedType = JsonSerializer.Deserialize("\"thinking\""); + + Assert.Equal(expectedSignature, deserialized.Signature); + Assert.Equal(expectedThinking, deserialized.Thinking); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new ThinkingBlockParam { Signature = "signature", Thinking = "thinking" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ThinkingBlockTest.cs b/src/Anthropic.Tests/Models/Messages/ThinkingBlockTest.cs new file mode 100644 index 00000000..0bde35e2 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ThinkingBlockTest.cs @@ -0,0 +1,58 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ThinkingBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ThinkingBlock { Signature = "signature", Thinking = "thinking" }; + + string expectedSignature = "signature"; + string expectedThinking = "thinking"; + JsonElement expectedType = JsonSerializer.Deserialize("\"thinking\""); + + Assert.Equal(expectedSignature, model.Signature); + Assert.Equal(expectedThinking, model.Thinking); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ThinkingBlock { Signature = "signature", Thinking = "thinking" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ThinkingBlock { Signature = "signature", Thinking = "thinking" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedSignature = "signature"; + string expectedThinking = "thinking"; + JsonElement expectedType = JsonSerializer.Deserialize("\"thinking\""); + + Assert.Equal(expectedSignature, deserialized.Signature); + Assert.Equal(expectedThinking, deserialized.Thinking); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new ThinkingBlock { Signature = "signature", Thinking = "thinking" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ThinkingConfigDisabledTest.cs b/src/Anthropic.Tests/Models/Messages/ThinkingConfigDisabledTest.cs new file mode 100644 index 00000000..6243ffcc --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ThinkingConfigDisabledTest.cs @@ -0,0 +1,50 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ThinkingConfigDisabledTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ThinkingConfigDisabled { }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"disabled\""); + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ThinkingConfigDisabled { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ThinkingConfigDisabled { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"disabled\""); + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new ThinkingConfigDisabled { }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ThinkingConfigEnabledTest.cs b/src/Anthropic.Tests/Models/Messages/ThinkingConfigEnabledTest.cs new file mode 100644 index 00000000..da5ad930 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ThinkingConfigEnabledTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ThinkingConfigEnabledTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ThinkingConfigEnabled { BudgetTokens = 1024 }; + + long expectedBudgetTokens = 1024; + JsonElement expectedType = JsonSerializer.Deserialize("\"enabled\""); + + Assert.Equal(expectedBudgetTokens, model.BudgetTokens); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ThinkingConfigEnabled { BudgetTokens = 1024 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ThinkingConfigEnabled { BudgetTokens = 1024 }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + long expectedBudgetTokens = 1024; + JsonElement expectedType = JsonSerializer.Deserialize("\"enabled\""); + + Assert.Equal(expectedBudgetTokens, deserialized.BudgetTokens); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new ThinkingConfigEnabled { BudgetTokens = 1024 }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ThinkingConfigParamTest.cs b/src/Anthropic.Tests/Models/Messages/ThinkingConfigParamTest.cs new file mode 100644 index 00000000..cec52f06 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ThinkingConfigParamTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Messages; diff --git a/src/Anthropic.Tests/Models/Messages/ThinkingDeltaTest.cs b/src/Anthropic.Tests/Models/Messages/ThinkingDeltaTest.cs new file mode 100644 index 00000000..848554b5 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ThinkingDeltaTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ThinkingDeltaTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ThinkingDelta { Thinking = "thinking" }; + + string expectedThinking = "thinking"; + JsonElement expectedType = JsonSerializer.Deserialize("\"thinking_delta\""); + + Assert.Equal(expectedThinking, model.Thinking); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ThinkingDelta { Thinking = "thinking" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ThinkingDelta { Thinking = "thinking" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedThinking = "thinking"; + JsonElement expectedType = JsonSerializer.Deserialize("\"thinking_delta\""); + + Assert.Equal(expectedThinking, deserialized.Thinking); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new ThinkingDelta { Thinking = "thinking" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ToolBash20250124Test.cs b/src/Anthropic.Tests/Models/Messages/ToolBash20250124Test.cs new file mode 100644 index 00000000..290030b6 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ToolBash20250124Test.cs @@ -0,0 +1,92 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ToolBash20250124Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ToolBash20250124 { CacheControl = new() { TTL = TTL.TTL5m } }; + + JsonElement expectedName = JsonSerializer.Deserialize("\"bash\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"bash_20250124\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ToolBash20250124 { CacheControl = new() { TTL = TTL.TTL5m } }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ToolBash20250124 { CacheControl = new() { TTL = TTL.TTL5m } }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize("\"bash\""); + JsonElement expectedType = JsonSerializer.Deserialize("\"bash_20250124\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new ToolBash20250124 { CacheControl = new() { TTL = TTL.TTL5m } }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new ToolBash20250124 { }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new ToolBash20250124 { }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new ToolBash20250124 { CacheControl = null }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new ToolBash20250124 { CacheControl = null }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ToolChoiceAnyTest.cs b/src/Anthropic.Tests/Models/Messages/ToolChoiceAnyTest.cs new file mode 100644 index 00000000..f40a956a --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ToolChoiceAnyTest.cs @@ -0,0 +1,96 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ToolChoiceAnyTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ToolChoiceAny { DisableParallelToolUse = true }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"any\""); + bool expectedDisableParallelToolUse = true; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedDisableParallelToolUse, model.DisableParallelToolUse); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ToolChoiceAny { DisableParallelToolUse = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ToolChoiceAny { DisableParallelToolUse = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"any\""); + bool expectedDisableParallelToolUse = true; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedDisableParallelToolUse, deserialized.DisableParallelToolUse); + } + + [Fact] + public void Validation_Works() + { + var model = new ToolChoiceAny { DisableParallelToolUse = true }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new ToolChoiceAny { }; + + Assert.Null(model.DisableParallelToolUse); + Assert.False(model.RawData.ContainsKey("disable_parallel_tool_use")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new ToolChoiceAny { }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new ToolChoiceAny + { + // Null should be interpreted as omitted for these properties + DisableParallelToolUse = null, + }; + + Assert.Null(model.DisableParallelToolUse); + Assert.False(model.RawData.ContainsKey("disable_parallel_tool_use")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new ToolChoiceAny + { + // Null should be interpreted as omitted for these properties + DisableParallelToolUse = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ToolChoiceAutoTest.cs b/src/Anthropic.Tests/Models/Messages/ToolChoiceAutoTest.cs new file mode 100644 index 00000000..1de479d3 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ToolChoiceAutoTest.cs @@ -0,0 +1,96 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ToolChoiceAutoTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ToolChoiceAuto { DisableParallelToolUse = true }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"auto\""); + bool expectedDisableParallelToolUse = true; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedDisableParallelToolUse, model.DisableParallelToolUse); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ToolChoiceAuto { DisableParallelToolUse = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ToolChoiceAuto { DisableParallelToolUse = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"auto\""); + bool expectedDisableParallelToolUse = true; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedDisableParallelToolUse, deserialized.DisableParallelToolUse); + } + + [Fact] + public void Validation_Works() + { + var model = new ToolChoiceAuto { DisableParallelToolUse = true }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new ToolChoiceAuto { }; + + Assert.Null(model.DisableParallelToolUse); + Assert.False(model.RawData.ContainsKey("disable_parallel_tool_use")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new ToolChoiceAuto { }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new ToolChoiceAuto + { + // Null should be interpreted as omitted for these properties + DisableParallelToolUse = null, + }; + + Assert.Null(model.DisableParallelToolUse); + Assert.False(model.RawData.ContainsKey("disable_parallel_tool_use")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new ToolChoiceAuto + { + // Null should be interpreted as omitted for these properties + DisableParallelToolUse = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ToolChoiceNoneTest.cs b/src/Anthropic.Tests/Models/Messages/ToolChoiceNoneTest.cs new file mode 100644 index 00000000..f8453bb7 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ToolChoiceNoneTest.cs @@ -0,0 +1,50 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ToolChoiceNoneTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ToolChoiceNone { }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"none\""); + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ToolChoiceNone { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ToolChoiceNone { }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"none\""); + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new ToolChoiceNone { }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ToolChoiceTest.cs b/src/Anthropic.Tests/Models/Messages/ToolChoiceTest.cs new file mode 100644 index 00000000..cec52f06 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ToolChoiceTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Messages; diff --git a/src/Anthropic.Tests/Models/Messages/ToolChoiceToolTest.cs b/src/Anthropic.Tests/Models/Messages/ToolChoiceToolTest.cs new file mode 100644 index 00000000..20a07ef4 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ToolChoiceToolTest.cs @@ -0,0 +1,104 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ToolChoiceToolTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ToolChoiceTool { Name = "name", DisableParallelToolUse = true }; + + string expectedName = "name"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool\""); + bool expectedDisableParallelToolUse = true; + + Assert.Equal(expectedName, model.Name); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedDisableParallelToolUse, model.DisableParallelToolUse); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ToolChoiceTool { Name = "name", DisableParallelToolUse = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ToolChoiceTool { Name = "name", DisableParallelToolUse = true }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedName = "name"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool\""); + bool expectedDisableParallelToolUse = true; + + Assert.Equal(expectedName, deserialized.Name); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedDisableParallelToolUse, deserialized.DisableParallelToolUse); + } + + [Fact] + public void Validation_Works() + { + var model = new ToolChoiceTool { Name = "name", DisableParallelToolUse = true }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new ToolChoiceTool { Name = "name" }; + + Assert.Null(model.DisableParallelToolUse); + Assert.False(model.RawData.ContainsKey("disable_parallel_tool_use")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new ToolChoiceTool { Name = "name" }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new ToolChoiceTool + { + Name = "name", + + // Null should be interpreted as omitted for these properties + DisableParallelToolUse = null, + }; + + Assert.Null(model.DisableParallelToolUse); + Assert.False(model.RawData.ContainsKey("disable_parallel_tool_use")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new ToolChoiceTool + { + Name = "name", + + // Null should be interpreted as omitted for these properties + DisableParallelToolUse = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ToolResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Messages/ToolResultBlockParamTest.cs new file mode 100644 index 00000000..d223af30 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ToolResultBlockParamTest.cs @@ -0,0 +1,210 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ToolResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + Content = "string", + IsError = true, + }; + + string expectedToolUseID = "tool_use_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_result\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + ToolResultBlockParamContent expectedContent = "string"; + bool expectedIsError = true; + + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedIsError, model.IsError); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + Content = "string", + IsError = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + Content = "string", + IsError = true, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedToolUseID = "tool_use_id"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_result\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + ToolResultBlockParamContent expectedContent = "string"; + bool expectedIsError = true; + + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedIsError, deserialized.IsError); + } + + [Fact] + public void Validation_Works() + { + var model = new ToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + Content = "string", + IsError = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new ToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + Assert.Null(model.Content); + Assert.False(model.RawData.ContainsKey("content")); + Assert.Null(model.IsError); + Assert.False(model.RawData.ContainsKey("is_error")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new ToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new ToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + Content = null, + IsError = null, + }; + + Assert.Null(model.Content); + Assert.False(model.RawData.ContainsKey("content")); + Assert.Null(model.IsError); + Assert.False(model.RawData.ContainsKey("is_error")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new ToolResultBlockParam + { + ToolUseID = "tool_use_id", + CacheControl = new() { TTL = TTL.TTL5m }, + + // Null should be interpreted as omitted for these properties + Content = null, + IsError = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new ToolResultBlockParam + { + ToolUseID = "tool_use_id", + Content = "string", + IsError = true, + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new ToolResultBlockParam + { + ToolUseID = "tool_use_id", + Content = "string", + IsError = true, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new ToolResultBlockParam + { + ToolUseID = "tool_use_id", + Content = "string", + IsError = true, + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new ToolResultBlockParam + { + ToolUseID = "tool_use_id", + Content = "string", + IsError = true, + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ToolTest.cs b/src/Anthropic.Tests/Models/Messages/ToolTest.cs new file mode 100644 index 00000000..c92701c0 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ToolTest.cs @@ -0,0 +1,543 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ToolTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Tool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Type.Custom, + }; + + InputSchema expectedInputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }; + string expectedName = "name"; + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + string expectedDescription = "Get the current weather in a given location"; + ApiEnum expectedType = Type.Custom; + + Assert.Equal(expectedInputSchema, model.InputSchema); + Assert.Equal(expectedName, model.Name); + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedDescription, model.Description); + Assert.Equal(expectedType, model.Type); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Tool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Type.Custom, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Tool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Type.Custom, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + InputSchema expectedInputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }; + string expectedName = "name"; + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + string expectedDescription = "Get the current weather in a given location"; + ApiEnum expectedType = Type.Custom; + + Assert.Equal(expectedInputSchema, deserialized.InputSchema); + Assert.Equal(expectedName, deserialized.Name); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedDescription, deserialized.Description); + Assert.Equal(expectedType, deserialized.Type); + } + + [Fact] + public void Validation_Works() + { + var model = new Tool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = TTL.TTL5m }, + Description = "Get the current weather in a given location", + Type = Type.Custom, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetAreNotSet_Works() + { + var model = new Tool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = TTL.TTL5m }, + Type = Type.Custom, + }; + + Assert.Null(model.Description); + Assert.False(model.RawData.ContainsKey("description")); + } + + [Fact] + public void OptionalNonNullablePropertiesUnsetValidation_Works() + { + var model = new Tool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = TTL.TTL5m }, + Type = Type.Custom, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullAreNotSet_Works() + { + var model = new Tool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = TTL.TTL5m }, + Type = Type.Custom, + + // Null should be interpreted as omitted for these properties + Description = null, + }; + + Assert.Null(model.Description); + Assert.False(model.RawData.ContainsKey("description")); + } + + [Fact] + public void OptionalNonNullablePropertiesSetToNullValidation_Works() + { + var model = new Tool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + CacheControl = new() { TTL = TTL.TTL5m }, + Type = Type.Custom, + + // Null should be interpreted as omitted for these properties + Description = null, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new Tool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + Description = "Get the current weather in a given location", + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Type); + Assert.False(model.RawData.ContainsKey("type")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new Tool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + Description = "Get the current weather in a given location", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new Tool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + Description = "Get the current weather in a given location", + + CacheControl = null, + Type = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.Type); + Assert.True(model.RawData.ContainsKey("type")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new Tool + { + InputSchema = new() + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }, + Name = "name", + Description = "Get the current weather in a given location", + + CacheControl = null, + Type = null, + }; + + model.Validate(); + } +} + +public class InputSchemaTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new InputSchema + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"object\""); + Dictionary expectedProperties = new() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }; + List expectedRequired = ["location"]; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedProperties.Count, model.Properties.Count); + foreach (var item in expectedProperties) + { + Assert.True(model.Properties.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.Properties[item.Key])); + } + Assert.Equal(expectedRequired.Count, model.Required.Count); + for (int i = 0; i < expectedRequired.Count; i++) + { + Assert.Equal(expectedRequired[i], model.Required[i]); + } + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new InputSchema + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new InputSchema + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"object\""); + Dictionary expectedProperties = new() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }; + List expectedRequired = ["location"]; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedProperties.Count, deserialized.Properties.Count); + foreach (var item in expectedProperties) + { + Assert.True(deserialized.Properties.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.Properties[item.Key])); + } + Assert.Equal(expectedRequired.Count, deserialized.Required.Count); + for (int i = 0; i < expectedRequired.Count; i++) + { + Assert.Equal(expectedRequired[i], deserialized.Required[i]); + } + } + + [Fact] + public void Validation_Works() + { + var model = new InputSchema + { + Properties = new Dictionary() + { + { "location", JsonSerializer.SerializeToElement("bar") }, + { "unit", JsonSerializer.SerializeToElement("bar") }, + }, + Required = ["location"], + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new InputSchema { }; + + Assert.Null(model.Properties); + Assert.False(model.RawData.ContainsKey("properties")); + Assert.Null(model.Required); + Assert.False(model.RawData.ContainsKey("required")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new InputSchema { }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new InputSchema { Properties = null, Required = null }; + + Assert.Null(model.Properties); + Assert.True(model.RawData.ContainsKey("properties")); + Assert.Null(model.Required); + Assert.True(model.RawData.ContainsKey("required")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new InputSchema { Properties = null, Required = null }; + + model.Validate(); + } +} + +public class TypeTest : TestBase +{ + [Theory] + [InlineData(Type.Custom)] + public void Validation_Works(Type rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(Type.Custom)] + public void SerializationRoundtrip_Works(Type rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ToolTextEditor20250124Test.cs b/src/Anthropic.Tests/Models/Messages/ToolTextEditor20250124Test.cs new file mode 100644 index 00000000..690e2ca7 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ToolTextEditor20250124Test.cs @@ -0,0 +1,100 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ToolTextEditor20250124Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ToolTextEditor20250124 { CacheControl = new() { TTL = TTL.TTL5m } }; + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"str_replace_editor\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_20250124\"" + ); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ToolTextEditor20250124 { CacheControl = new() { TTL = TTL.TTL5m } }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ToolTextEditor20250124 { CacheControl = new() { TTL = TTL.TTL5m } }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"str_replace_editor\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_20250124\"" + ); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new ToolTextEditor20250124 { CacheControl = new() { TTL = TTL.TTL5m } }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new ToolTextEditor20250124 { }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new ToolTextEditor20250124 { }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new ToolTextEditor20250124 { CacheControl = null }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new ToolTextEditor20250124 { CacheControl = null }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ToolTextEditor20250429Test.cs b/src/Anthropic.Tests/Models/Messages/ToolTextEditor20250429Test.cs new file mode 100644 index 00000000..793bfe32 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ToolTextEditor20250429Test.cs @@ -0,0 +1,100 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ToolTextEditor20250429Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ToolTextEditor20250429 { CacheControl = new() { TTL = TTL.TTL5m } }; + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"str_replace_based_edit_tool\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_20250429\"" + ); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ToolTextEditor20250429 { CacheControl = new() { TTL = TTL.TTL5m } }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ToolTextEditor20250429 { CacheControl = new() { TTL = TTL.TTL5m } }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"str_replace_based_edit_tool\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_20250429\"" + ); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new ToolTextEditor20250429 { CacheControl = new() { TTL = TTL.TTL5m } }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new ToolTextEditor20250429 { }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new ToolTextEditor20250429 { }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new ToolTextEditor20250429 { CacheControl = null }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new ToolTextEditor20250429 { CacheControl = null }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ToolTextEditor20250728Test.cs b/src/Anthropic.Tests/Models/Messages/ToolTextEditor20250728Test.cs new file mode 100644 index 00000000..3b24ff4c --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ToolTextEditor20250728Test.cs @@ -0,0 +1,124 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ToolTextEditor20250728Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ToolTextEditor20250728 + { + CacheControl = new() { TTL = TTL.TTL5m }, + MaxCharacters = 1, + }; + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"str_replace_based_edit_tool\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_20250728\"" + ); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + long expectedMaxCharacters = 1; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedMaxCharacters, model.MaxCharacters); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ToolTextEditor20250728 + { + CacheControl = new() { TTL = TTL.TTL5m }, + MaxCharacters = 1, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ToolTextEditor20250728 + { + CacheControl = new() { TTL = TTL.TTL5m }, + MaxCharacters = 1, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize( + "\"str_replace_based_edit_tool\"" + ); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"text_editor_20250728\"" + ); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + long expectedMaxCharacters = 1; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedMaxCharacters, deserialized.MaxCharacters); + } + + [Fact] + public void Validation_Works() + { + var model = new ToolTextEditor20250728 + { + CacheControl = new() { TTL = TTL.TTL5m }, + MaxCharacters = 1, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new ToolTextEditor20250728 { }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.MaxCharacters); + Assert.False(model.RawData.ContainsKey("max_characters")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new ToolTextEditor20250728 { }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new ToolTextEditor20250728 { CacheControl = null, MaxCharacters = null }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.MaxCharacters); + Assert.True(model.RawData.ContainsKey("max_characters")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new ToolTextEditor20250728 { CacheControl = null, MaxCharacters = null }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ToolUnionTest.cs b/src/Anthropic.Tests/Models/Messages/ToolUnionTest.cs new file mode 100644 index 00000000..cec52f06 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ToolUnionTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Messages; diff --git a/src/Anthropic.Tests/Models/Messages/ToolUseBlockParamTest.cs b/src/Anthropic.Tests/Models/Messages/ToolUseBlockParamTest.cs new file mode 100644 index 00000000..0b93ab02 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ToolUseBlockParamTest.cs @@ -0,0 +1,191 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ToolUseBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string expectedID = "id"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + string expectedName = "x"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_use\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedInput.Count, model.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(model.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.Input[item.Key])); + } + Assert.Equal(expectedName, model.Name); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "id"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + string expectedName = "x"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_use\""); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedInput.Count, deserialized.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(deserialized.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.Input[item.Key])); + } + Assert.Equal(expectedName, deserialized.Name); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new ToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new ToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new ToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new ToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new ToolUseBlockParam + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/ToolUseBlockTest.cs b/src/Anthropic.Tests/Models/Messages/ToolUseBlockTest.cs new file mode 100644 index 00000000..d8c7045b --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/ToolUseBlockTest.cs @@ -0,0 +1,113 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class ToolUseBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + }; + + string expectedID = "id"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + string expectedName = "x"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_use\""); + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedInput.Count, model.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(model.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, model.Input[item.Key])); + } + Assert.Equal(expectedName, model.Name); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "id"; + Dictionary expectedInput = new() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }; + string expectedName = "x"; + JsonElement expectedType = JsonSerializer.Deserialize("\"tool_use\""); + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedInput.Count, deserialized.Input.Count); + foreach (var item in expectedInput) + { + Assert.True(deserialized.Input.TryGetValue(item.Key, out var value)); + + Assert.True(JsonElement.DeepEquals(value, deserialized.Input[item.Key])); + } + Assert.Equal(expectedName, deserialized.Name); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new ToolUseBlock + { + ID = "id", + Input = new Dictionary() + { + { "foo", JsonSerializer.SerializeToElement("bar") }, + }, + Name = "x", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/URLImageSourceTest.cs b/src/Anthropic.Tests/Models/Messages/URLImageSourceTest.cs new file mode 100644 index 00000000..4099f296 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/URLImageSourceTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class URLImageSourceTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new URLImageSource { URL = "url" }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"url\""); + string expectedURL = "url"; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedURL, model.URL); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new URLImageSource { URL = "url" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new URLImageSource { URL = "url" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"url\""); + string expectedURL = "url"; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedURL, deserialized.URL); + } + + [Fact] + public void Validation_Works() + { + var model = new URLImageSource { URL = "url" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/URLPDFSourceTest.cs b/src/Anthropic.Tests/Models/Messages/URLPDFSourceTest.cs new file mode 100644 index 00000000..59b45c4a --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/URLPDFSourceTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class URLPDFSourceTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new URLPDFSource { URL = "url" }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"url\""); + string expectedURL = "url"; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedURL, model.URL); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new URLPDFSource { URL = "url" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new URLPDFSource { URL = "url" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"url\""); + string expectedURL = "url"; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedURL, deserialized.URL); + } + + [Fact] + public void Validation_Works() + { + var model = new URLPDFSource { URL = "url" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/UsageTest.cs b/src/Anthropic.Tests/Models/Messages/UsageTest.cs new file mode 100644 index 00000000..3b5bee78 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/UsageTest.cs @@ -0,0 +1,178 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class UsageTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new Usage + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }; + + CacheCreation expectedCacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }; + long expectedCacheCreationInputTokens = 2051; + long expectedCacheReadInputTokens = 2051; + long expectedInputTokens = 2095; + long expectedOutputTokens = 503; + ServerToolUsage expectedServerToolUse = new(0); + ApiEnum expectedServiceTier = UsageServiceTier.Standard; + + Assert.Equal(expectedCacheCreation, model.CacheCreation); + Assert.Equal(expectedCacheCreationInputTokens, model.CacheCreationInputTokens); + Assert.Equal(expectedCacheReadInputTokens, model.CacheReadInputTokens); + Assert.Equal(expectedInputTokens, model.InputTokens); + Assert.Equal(expectedOutputTokens, model.OutputTokens); + Assert.Equal(expectedServerToolUse, model.ServerToolUse); + Assert.Equal(expectedServiceTier, model.ServiceTier); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new Usage + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new Usage + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + CacheCreation expectedCacheCreation = new() + { + Ephemeral1hInputTokens = 0, + Ephemeral5mInputTokens = 0, + }; + long expectedCacheCreationInputTokens = 2051; + long expectedCacheReadInputTokens = 2051; + long expectedInputTokens = 2095; + long expectedOutputTokens = 503; + ServerToolUsage expectedServerToolUse = new(0); + ApiEnum expectedServiceTier = UsageServiceTier.Standard; + + Assert.Equal(expectedCacheCreation, deserialized.CacheCreation); + Assert.Equal(expectedCacheCreationInputTokens, deserialized.CacheCreationInputTokens); + Assert.Equal(expectedCacheReadInputTokens, deserialized.CacheReadInputTokens); + Assert.Equal(expectedInputTokens, deserialized.InputTokens); + Assert.Equal(expectedOutputTokens, deserialized.OutputTokens); + Assert.Equal(expectedServerToolUse, deserialized.ServerToolUse); + Assert.Equal(expectedServiceTier, deserialized.ServiceTier); + } + + [Fact] + public void Validation_Works() + { + var model = new Usage + { + CacheCreation = new() { Ephemeral1hInputTokens = 0, Ephemeral5mInputTokens = 0 }, + CacheCreationInputTokens = 2051, + CacheReadInputTokens = 2051, + InputTokens = 2095, + OutputTokens = 503, + ServerToolUse = new(0), + ServiceTier = UsageServiceTier.Standard, + }; + + model.Validate(); + } +} + +public class UsageServiceTierTest : TestBase +{ + [Theory] + [InlineData(UsageServiceTier.Standard)] + [InlineData(UsageServiceTier.Priority)] + [InlineData(UsageServiceTier.Batch)] + public void Validation_Works(UsageServiceTier rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(UsageServiceTier.Standard)] + [InlineData(UsageServiceTier.Priority)] + [InlineData(UsageServiceTier.Batch)] + public void SerializationRoundtrip_Works(UsageServiceTier rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/WebSearchResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Messages/WebSearchResultBlockParamTest.cs new file mode 100644 index 00000000..ee38c41b --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/WebSearchResultBlockParamTest.cs @@ -0,0 +1,148 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class WebSearchResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new WebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }; + + string expectedEncryptedContent = "encrypted_content"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize("\"web_search_result\""); + string expectedURL = "url"; + string expectedPageAge = "page_age"; + + Assert.Equal(expectedEncryptedContent, model.EncryptedContent); + Assert.Equal(expectedTitle, model.Title); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedURL, model.URL); + Assert.Equal(expectedPageAge, model.PageAge); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new WebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new WebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedEncryptedContent = "encrypted_content"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize("\"web_search_result\""); + string expectedURL = "url"; + string expectedPageAge = "page_age"; + + Assert.Equal(expectedEncryptedContent, deserialized.EncryptedContent); + Assert.Equal(expectedTitle, deserialized.Title); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedURL, deserialized.URL); + Assert.Equal(expectedPageAge, deserialized.PageAge); + } + + [Fact] + public void Validation_Works() + { + var model = new WebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new WebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + }; + + Assert.Null(model.PageAge); + Assert.False(model.RawData.ContainsKey("page_age")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new WebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new WebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + + PageAge = null, + }; + + Assert.Null(model.PageAge); + Assert.True(model.RawData.ContainsKey("page_age")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new WebSearchResultBlockParam + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + + PageAge = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/WebSearchResultBlockTest.cs b/src/Anthropic.Tests/Models/Messages/WebSearchResultBlockTest.cs new file mode 100644 index 00000000..9e90289a --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/WebSearchResultBlockTest.cs @@ -0,0 +1,90 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class WebSearchResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new WebSearchResultBlock + { + EncryptedContent = "encrypted_content", + PageAge = "page_age", + Title = "title", + URL = "url", + }; + + string expectedEncryptedContent = "encrypted_content"; + string expectedPageAge = "page_age"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize("\"web_search_result\""); + string expectedURL = "url"; + + Assert.Equal(expectedEncryptedContent, model.EncryptedContent); + Assert.Equal(expectedPageAge, model.PageAge); + Assert.Equal(expectedTitle, model.Title); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedURL, model.URL); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new WebSearchResultBlock + { + EncryptedContent = "encrypted_content", + PageAge = "page_age", + Title = "title", + URL = "url", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new WebSearchResultBlock + { + EncryptedContent = "encrypted_content", + PageAge = "page_age", + Title = "title", + URL = "url", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedEncryptedContent = "encrypted_content"; + string expectedPageAge = "page_age"; + string expectedTitle = "title"; + JsonElement expectedType = JsonSerializer.Deserialize("\"web_search_result\""); + string expectedURL = "url"; + + Assert.Equal(expectedEncryptedContent, deserialized.EncryptedContent); + Assert.Equal(expectedPageAge, deserialized.PageAge); + Assert.Equal(expectedTitle, deserialized.Title); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedURL, deserialized.URL); + } + + [Fact] + public void Validation_Works() + { + var model = new WebSearchResultBlock + { + EncryptedContent = "encrypted_content", + PageAge = "page_age", + Title = "title", + URL = "url", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/WebSearchTool20250305Test.cs b/src/Anthropic.Tests/Models/Messages/WebSearchTool20250305Test.cs new file mode 100644 index 00000000..a3e67d16 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/WebSearchTool20250305Test.cs @@ -0,0 +1,367 @@ +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class WebSearchTool20250305Test : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new WebSearchTool20250305 + { + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + MaxUses = 1, + UserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }, + }; + + JsonElement expectedName = JsonSerializer.Deserialize("\"web_search\""); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_20250305\"" + ); + List expectedAllowedDomains = ["string"]; + List expectedBlockedDomains = ["string"]; + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + long expectedMaxUses = 1; + UserLocation expectedUserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }; + + Assert.True(JsonElement.DeepEquals(expectedName, model.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedAllowedDomains.Count, model.AllowedDomains.Count); + for (int i = 0; i < expectedAllowedDomains.Count; i++) + { + Assert.Equal(expectedAllowedDomains[i], model.AllowedDomains[i]); + } + Assert.Equal(expectedBlockedDomains.Count, model.BlockedDomains.Count); + for (int i = 0; i < expectedBlockedDomains.Count; i++) + { + Assert.Equal(expectedBlockedDomains[i], model.BlockedDomains[i]); + } + Assert.Equal(expectedCacheControl, model.CacheControl); + Assert.Equal(expectedMaxUses, model.MaxUses); + Assert.Equal(expectedUserLocation, model.UserLocation); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new WebSearchTool20250305 + { + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + MaxUses = 1, + UserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new WebSearchTool20250305 + { + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + MaxUses = 1, + UserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedName = JsonSerializer.Deserialize("\"web_search\""); + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_20250305\"" + ); + List expectedAllowedDomains = ["string"]; + List expectedBlockedDomains = ["string"]; + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + long expectedMaxUses = 1; + UserLocation expectedUserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }; + + Assert.True(JsonElement.DeepEquals(expectedName, deserialized.Name)); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedAllowedDomains.Count, deserialized.AllowedDomains.Count); + for (int i = 0; i < expectedAllowedDomains.Count; i++) + { + Assert.Equal(expectedAllowedDomains[i], deserialized.AllowedDomains[i]); + } + Assert.Equal(expectedBlockedDomains.Count, deserialized.BlockedDomains.Count); + for (int i = 0; i < expectedBlockedDomains.Count; i++) + { + Assert.Equal(expectedBlockedDomains[i], deserialized.BlockedDomains[i]); + } + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + Assert.Equal(expectedMaxUses, deserialized.MaxUses); + Assert.Equal(expectedUserLocation, deserialized.UserLocation); + } + + [Fact] + public void Validation_Works() + { + var model = new WebSearchTool20250305 + { + AllowedDomains = ["string"], + BlockedDomains = ["string"], + CacheControl = new() { TTL = TTL.TTL5m }, + MaxUses = 1, + UserLocation = new() + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new WebSearchTool20250305 { }; + + Assert.Null(model.AllowedDomains); + Assert.False(model.RawData.ContainsKey("allowed_domains")); + Assert.Null(model.BlockedDomains); + Assert.False(model.RawData.ContainsKey("blocked_domains")); + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.MaxUses); + Assert.False(model.RawData.ContainsKey("max_uses")); + Assert.Null(model.UserLocation); + Assert.False(model.RawData.ContainsKey("user_location")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new WebSearchTool20250305 { }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new WebSearchTool20250305 + { + AllowedDomains = null, + BlockedDomains = null, + CacheControl = null, + MaxUses = null, + UserLocation = null, + }; + + Assert.Null(model.AllowedDomains); + Assert.True(model.RawData.ContainsKey("allowed_domains")); + Assert.Null(model.BlockedDomains); + Assert.True(model.RawData.ContainsKey("blocked_domains")); + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + Assert.Null(model.MaxUses); + Assert.True(model.RawData.ContainsKey("max_uses")); + Assert.Null(model.UserLocation); + Assert.True(model.RawData.ContainsKey("user_location")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new WebSearchTool20250305 + { + AllowedDomains = null, + BlockedDomains = null, + CacheControl = null, + MaxUses = null, + UserLocation = null, + }; + + model.Validate(); + } +} + +public class UserLocationTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new UserLocation + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }; + + JsonElement expectedType = JsonSerializer.Deserialize("\"approximate\""); + string expectedCity = "New York"; + string expectedCountry = "US"; + string expectedRegion = "California"; + string expectedTimezone = "America/New_York"; + + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCity, model.City); + Assert.Equal(expectedCountry, model.Country); + Assert.Equal(expectedRegion, model.Region); + Assert.Equal(expectedTimezone, model.Timezone); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new UserLocation + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new UserLocation + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + JsonElement expectedType = JsonSerializer.Deserialize("\"approximate\""); + string expectedCity = "New York"; + string expectedCountry = "US"; + string expectedRegion = "California"; + string expectedTimezone = "America/New_York"; + + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCity, deserialized.City); + Assert.Equal(expectedCountry, deserialized.Country); + Assert.Equal(expectedRegion, deserialized.Region); + Assert.Equal(expectedTimezone, deserialized.Timezone); + } + + [Fact] + public void Validation_Works() + { + var model = new UserLocation + { + City = "New York", + Country = "US", + Region = "California", + Timezone = "America/New_York", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new UserLocation { }; + + Assert.Null(model.City); + Assert.False(model.RawData.ContainsKey("city")); + Assert.Null(model.Country); + Assert.False(model.RawData.ContainsKey("country")); + Assert.Null(model.Region); + Assert.False(model.RawData.ContainsKey("region")); + Assert.Null(model.Timezone); + Assert.False(model.RawData.ContainsKey("timezone")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new UserLocation { }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new UserLocation + { + City = null, + Country = null, + Region = null, + Timezone = null, + }; + + Assert.Null(model.City); + Assert.True(model.RawData.ContainsKey("city")); + Assert.Null(model.Country); + Assert.True(model.RawData.ContainsKey("country")); + Assert.Null(model.Region); + Assert.True(model.RawData.ContainsKey("region")); + Assert.Null(model.Timezone); + Assert.True(model.RawData.ContainsKey("timezone")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new UserLocation + { + City = null, + Country = null, + Region = null, + Timezone = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/WebSearchToolRequestErrorTest.cs b/src/Anthropic.Tests/Models/Messages/WebSearchToolRequestErrorTest.cs new file mode 100644 index 00000000..b22b55d1 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/WebSearchToolRequestErrorTest.cs @@ -0,0 +1,122 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class WebSearchToolRequestErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new WebSearchToolRequestError { ErrorCode = ErrorCode.InvalidToolInput }; + + ApiEnum expectedErrorCode = ErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, model.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new WebSearchToolRequestError { ErrorCode = ErrorCode.InvalidToolInput }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new WebSearchToolRequestError { ErrorCode = ErrorCode.InvalidToolInput }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ApiEnum expectedErrorCode = ErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, deserialized.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new WebSearchToolRequestError { ErrorCode = ErrorCode.InvalidToolInput }; + + model.Validate(); + } +} + +public class ErrorCodeTest : TestBase +{ + [Theory] + [InlineData(ErrorCode.InvalidToolInput)] + [InlineData(ErrorCode.Unavailable)] + [InlineData(ErrorCode.MaxUsesExceeded)] + [InlineData(ErrorCode.TooManyRequests)] + [InlineData(ErrorCode.QueryTooLong)] + public void Validation_Works(ErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(ErrorCode.InvalidToolInput)] + [InlineData(ErrorCode.Unavailable)] + [InlineData(ErrorCode.MaxUsesExceeded)] + [InlineData(ErrorCode.TooManyRequests)] + [InlineData(ErrorCode.QueryTooLong)] + public void SerializationRoundtrip_Works(ErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize>( + json, + ModelBase.SerializerOptions + ); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/WebSearchToolResultBlockContentTest.cs b/src/Anthropic.Tests/Models/Messages/WebSearchToolResultBlockContentTest.cs new file mode 100644 index 00000000..cec52f06 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/WebSearchToolResultBlockContentTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Messages; diff --git a/src/Anthropic.Tests/Models/Messages/WebSearchToolResultBlockParamContentTest.cs b/src/Anthropic.Tests/Models/Messages/WebSearchToolResultBlockParamContentTest.cs new file mode 100644 index 00000000..cec52f06 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/WebSearchToolResultBlockParamContentTest.cs @@ -0,0 +1 @@ +namespace Anthropic.Tests.Models.Messages; diff --git a/src/Anthropic.Tests/Models/Messages/WebSearchToolResultBlockParamTest.cs b/src/Anthropic.Tests/Models/Messages/WebSearchToolResultBlockParamTest.cs new file mode 100644 index 00000000..26f7f8dd --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/WebSearchToolResultBlockParamTest.cs @@ -0,0 +1,240 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class WebSearchToolResultBlockParamTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new WebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + WebSearchToolResultBlockParamContent expectedContent = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result\"" + ); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + Assert.Equal(expectedCacheControl, model.CacheControl); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new WebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new WebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + WebSearchToolResultBlockParamContent expectedContent = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result\"" + ); + CacheControlEphemeral expectedCacheControl = new() { TTL = TTL.TTL5m }; + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + Assert.Equal(expectedCacheControl, deserialized.CacheControl); + } + + [Fact] + public void Validation_Works() + { + var model = new WebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + CacheControl = new() { TTL = TTL.TTL5m }, + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesUnsetAreNotSet_Works() + { + var model = new WebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + Assert.Null(model.CacheControl); + Assert.False(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesUnsetValidation_Works() + { + var model = new WebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + model.Validate(); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullAreSetToNull_Works() + { + var model = new WebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + + CacheControl = null, + }; + + Assert.Null(model.CacheControl); + Assert.True(model.RawData.ContainsKey("cache_control")); + } + + [Fact] + public void OptionalNullablePropertiesSetToNullValidation_Works() + { + var model = new WebSearchToolResultBlockParam + { + Content = new( + [ + new() + { + EncryptedContent = "encrypted_content", + Title = "title", + URL = "url", + PageAge = "page_age", + }, + ] + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + + CacheControl = null, + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/WebSearchToolResultBlockTest.cs b/src/Anthropic.Tests/Models/Messages/WebSearchToolResultBlockTest.cs new file mode 100644 index 00000000..0a96ffbe --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/WebSearchToolResultBlockTest.cs @@ -0,0 +1,90 @@ +using System.Text.Json; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class WebSearchToolResultBlockTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new WebSearchToolResultBlock + { + Content = new WebSearchToolResultError( + WebSearchToolResultErrorErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + WebSearchToolResultBlockContent expectedContent = new WebSearchToolResultError( + WebSearchToolResultErrorErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result\"" + ); + + Assert.Equal(expectedContent, model.Content); + Assert.Equal(expectedToolUseID, model.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new WebSearchToolResultBlock + { + Content = new WebSearchToolResultError( + WebSearchToolResultErrorErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new WebSearchToolResultBlock + { + Content = new WebSearchToolResultError( + WebSearchToolResultErrorErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + WebSearchToolResultBlockContent expectedContent = new WebSearchToolResultError( + WebSearchToolResultErrorErrorCode.InvalidToolInput + ); + string expectedToolUseID = "srvtoolu_SQfNkl1n_JR_"; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result\"" + ); + + Assert.Equal(expectedContent, deserialized.Content); + Assert.Equal(expectedToolUseID, deserialized.ToolUseID); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new WebSearchToolResultBlock + { + Content = new WebSearchToolResultError( + WebSearchToolResultErrorErrorCode.InvalidToolInput + ), + ToolUseID = "srvtoolu_SQfNkl1n_JR_", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Messages/WebSearchToolResultErrorTest.cs b/src/Anthropic.Tests/Models/Messages/WebSearchToolResultErrorTest.cs new file mode 100644 index 00000000..f9b85b86 --- /dev/null +++ b/src/Anthropic.Tests/Models/Messages/WebSearchToolResultErrorTest.cs @@ -0,0 +1,134 @@ +using System.Text.Json; +using Anthropic.Core; +using Anthropic.Exceptions; +using Anthropic.Models.Messages; + +namespace Anthropic.Tests.Models.Messages; + +public class WebSearchToolResultErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new WebSearchToolResultError + { + ErrorCode = WebSearchToolResultErrorErrorCode.InvalidToolInput, + }; + + ApiEnum expectedErrorCode = + WebSearchToolResultErrorErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, model.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new WebSearchToolResultError + { + ErrorCode = WebSearchToolResultErrorErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new WebSearchToolResultError + { + ErrorCode = WebSearchToolResultErrorErrorCode.InvalidToolInput, + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + ApiEnum expectedErrorCode = + WebSearchToolResultErrorErrorCode.InvalidToolInput; + JsonElement expectedType = JsonSerializer.Deserialize( + "\"web_search_tool_result_error\"" + ); + + Assert.Equal(expectedErrorCode, deserialized.ErrorCode); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new WebSearchToolResultError + { + ErrorCode = WebSearchToolResultErrorErrorCode.InvalidToolInput, + }; + + model.Validate(); + } +} + +public class WebSearchToolResultErrorErrorCodeTest : TestBase +{ + [Theory] + [InlineData(WebSearchToolResultErrorErrorCode.InvalidToolInput)] + [InlineData(WebSearchToolResultErrorErrorCode.Unavailable)] + [InlineData(WebSearchToolResultErrorErrorCode.MaxUsesExceeded)] + [InlineData(WebSearchToolResultErrorErrorCode.TooManyRequests)] + [InlineData(WebSearchToolResultErrorErrorCode.QueryTooLong)] + public void Validation_Works(WebSearchToolResultErrorErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + value.Validate(); + } + + [Fact] + public void InvalidEnumValidationThrows_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + Assert.Throws(() => value.Validate()); + } + + [Theory] + [InlineData(WebSearchToolResultErrorErrorCode.InvalidToolInput)] + [InlineData(WebSearchToolResultErrorErrorCode.Unavailable)] + [InlineData(WebSearchToolResultErrorErrorCode.MaxUsesExceeded)] + [InlineData(WebSearchToolResultErrorErrorCode.TooManyRequests)] + [InlineData(WebSearchToolResultErrorErrorCode.QueryTooLong)] + public void SerializationRoundtrip_Works(WebSearchToolResultErrorErrorCode rawValue) + { + // force implicit conversion because Theory can't do that for us + ApiEnum value = rawValue; + + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } + + [Fact] + public void InvalidEnumSerializationRoundtrip_Works() + { + var value = JsonSerializer.Deserialize>( + JsonSerializer.Deserialize("\"invalid value\""), + ModelBase.SerializerOptions + ); + string json = JsonSerializer.Serialize(value, ModelBase.SerializerOptions); + var deserialized = JsonSerializer.Deserialize< + ApiEnum + >(json, ModelBase.SerializerOptions); + + Assert.Equal(value, deserialized); + } +} diff --git a/src/Anthropic.Tests/Models/Models/ModelInfoTest.cs b/src/Anthropic.Tests/Models/Models/ModelInfoTest.cs new file mode 100644 index 00000000..64d9c9ac --- /dev/null +++ b/src/Anthropic.Tests/Models/Models/ModelInfoTest.cs @@ -0,0 +1,83 @@ +using System; +using System.Text.Json; +using Anthropic.Models.Models; + +namespace Anthropic.Tests.Models.Models; + +public class ModelInfoTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ModelInfo + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }; + + string expectedID = "claude-sonnet-4-20250514"; + DateTimeOffset expectedCreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"); + string expectedDisplayName = "Claude Sonnet 4"; + JsonElement expectedType = JsonSerializer.Deserialize("\"model\""); + + Assert.Equal(expectedID, model.ID); + Assert.Equal(expectedCreatedAt, model.CreatedAt); + Assert.Equal(expectedDisplayName, model.DisplayName); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ModelInfo + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ModelInfo + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedID = "claude-sonnet-4-20250514"; + DateTimeOffset expectedCreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"); + string expectedDisplayName = "Claude Sonnet 4"; + JsonElement expectedType = JsonSerializer.Deserialize("\"model\""); + + Assert.Equal(expectedID, deserialized.ID); + Assert.Equal(expectedCreatedAt, deserialized.CreatedAt); + Assert.Equal(expectedDisplayName, deserialized.DisplayName); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new ModelInfo + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/Models/ModelListPageResponseTest.cs b/src/Anthropic.Tests/Models/Models/ModelListPageResponseTest.cs new file mode 100644 index 00000000..19d4516d --- /dev/null +++ b/src/Anthropic.Tests/Models/Models/ModelListPageResponseTest.cs @@ -0,0 +1,144 @@ +using System; +using System.Collections.Generic; +using System.Text.Json; +using Anthropic.Models.Models; + +namespace Anthropic.Tests.Models.Models; + +public class ModelListPageResponseTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new ModelListPageResponse + { + Data = + [ + new() + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + List expectedData = + [ + new() + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }, + ]; + string expectedFirstID = "first_id"; + bool expectedHasMore = true; + string expectedLastID = "last_id"; + + Assert.Equal(expectedData.Count, model.Data.Count); + for (int i = 0; i < expectedData.Count; i++) + { + Assert.Equal(expectedData[i], model.Data[i]); + } + Assert.Equal(expectedFirstID, model.FirstID); + Assert.Equal(expectedHasMore, model.HasMore); + Assert.Equal(expectedLastID, model.LastID); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new ModelListPageResponse + { + Data = + [ + new() + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new ModelListPageResponse + { + Data = + [ + new() + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + List expectedData = + [ + new() + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }, + ]; + string expectedFirstID = "first_id"; + bool expectedHasMore = true; + string expectedLastID = "last_id"; + + Assert.Equal(expectedData.Count, deserialized.Data.Count); + for (int i = 0; i < expectedData.Count; i++) + { + Assert.Equal(expectedData[i], deserialized.Data[i]); + } + Assert.Equal(expectedFirstID, deserialized.FirstID); + Assert.Equal(expectedHasMore, deserialized.HasMore); + Assert.Equal(expectedLastID, deserialized.LastID); + } + + [Fact] + public void Validation_Works() + { + var model = new ModelListPageResponse + { + Data = + [ + new() + { + ID = "claude-sonnet-4-20250514", + CreatedAt = DateTimeOffset.Parse("2025-02-19T00:00:00Z"), + DisplayName = "Claude Sonnet 4", + }, + ], + FirstID = "first_id", + HasMore = true, + LastID = "last_id", + }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/NotFoundErrorTest.cs b/src/Anthropic.Tests/Models/NotFoundErrorTest.cs new file mode 100644 index 00000000..5eb07c2a --- /dev/null +++ b/src/Anthropic.Tests/Models/NotFoundErrorTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models; + +namespace Anthropic.Tests.Models; + +public class NotFoundErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new NotFoundError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"not_found_error\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new NotFoundError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new NotFoundError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"not_found_error\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new NotFoundError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/OverloadedErrorTest.cs b/src/Anthropic.Tests/Models/OverloadedErrorTest.cs new file mode 100644 index 00000000..827375d8 --- /dev/null +++ b/src/Anthropic.Tests/Models/OverloadedErrorTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models; + +namespace Anthropic.Tests.Models; + +public class OverloadedErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new OverloadedError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"overloaded_error\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new OverloadedError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new OverloadedError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"overloaded_error\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new OverloadedError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/PermissionErrorTest.cs b/src/Anthropic.Tests/Models/PermissionErrorTest.cs new file mode 100644 index 00000000..7015dad9 --- /dev/null +++ b/src/Anthropic.Tests/Models/PermissionErrorTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models; + +namespace Anthropic.Tests.Models; + +public class PermissionErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new PermissionError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"permission_error\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new PermissionError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new PermissionError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"permission_error\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new PermissionError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Models/RateLimitErrorTest.cs b/src/Anthropic.Tests/Models/RateLimitErrorTest.cs new file mode 100644 index 00000000..a31f8032 --- /dev/null +++ b/src/Anthropic.Tests/Models/RateLimitErrorTest.cs @@ -0,0 +1,54 @@ +using System.Text.Json; +using Anthropic.Models; + +namespace Anthropic.Tests.Models; + +public class RateLimitErrorTest : TestBase +{ + [Fact] + public void FieldRoundtrip_Works() + { + var model = new RateLimitError { Message = "message" }; + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"rate_limit_error\""); + + Assert.Equal(expectedMessage, model.Message); + Assert.True(JsonElement.DeepEquals(expectedType, model.Type)); + } + + [Fact] + public void SerializationRoundtrip_Works() + { + var model = new RateLimitError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + + Assert.Equal(model, deserialized); + } + + [Fact] + public void FieldRoundtripThroughSerialization_Works() + { + var model = new RateLimitError { Message = "message" }; + + string json = JsonSerializer.Serialize(model); + var deserialized = JsonSerializer.Deserialize(json); + Assert.NotNull(deserialized); + + string expectedMessage = "message"; + JsonElement expectedType = JsonSerializer.Deserialize("\"rate_limit_error\""); + + Assert.Equal(expectedMessage, deserialized.Message); + Assert.True(JsonElement.DeepEquals(expectedType, deserialized.Type)); + } + + [Fact] + public void Validation_Works() + { + var model = new RateLimitError { Message = "message" }; + + model.Validate(); + } +} diff --git a/src/Anthropic.Tests/Services/Beta/Messages/BatchServiceTest.cs b/src/Anthropic.Tests/Services/Beta/Messages/BatchServiceTest.cs index b6332306..14560dcf 100644 --- a/src/Anthropic.Tests/Services/Beta/Messages/BatchServiceTest.cs +++ b/src/Anthropic.Tests/Services/Beta/Messages/BatchServiceTest.cs @@ -1,9 +1,9 @@ using System.Collections.Generic; using System.Text.Json; using System.Threading.Tasks; -using Anthropic.Models.Beta.Messages.Batches; -using Anthropic.Tests; -using Messages = Anthropic.Models.Beta.Messages; +using Anthropic.Models.Beta.Messages; +using Batches = Anthropic.Models.Beta.Messages.Batches; +using Messages = Anthropic.Models.Messages; namespace Anthropic.Tests.Services.Beta.Messages; @@ -24,12 +24,9 @@ public async Task Create_Works(IAnthropicClient client) Params = new() { MaxTokens = 1024, - Messages = - [ - new() { Content = "Hello, world", Role = Messages::Role.User }, - ], - Model = global::Anthropic.Models.Messages.Model.ClaudeOpus4_5_20251101, - Container = new Messages::BetaContainerParams() + Messages = [new() { Content = "Hello, world", Role = Role.User }], + Model = Messages::Model.ClaudeOpus4_5_20251101, + Container = new BetaContainerParams() { ID = "id", Skills = @@ -37,7 +34,7 @@ public async Task Create_Works(IAnthropicClient client) new() { SkillID = "x", - Type = Messages::BetaSkillParamsType.Anthropic, + Type = BetaSkillParamsType.Anthropic, Version = "x", }, ], @@ -46,13 +43,13 @@ public async Task Create_Works(IAnthropicClient client) { Edits = [ - new Messages::BetaClearToolUses20250919Edit() + new BetaClearToolUses20250919Edit() { ClearAtLeast = new(0), ClearToolInputs = true, ExcludeTools = ["string"], Keep = new(0), - Trigger = new Messages::BetaInputTokensTrigger(1), + Trigger = new BetaInputTokensTrigger(1), }, ], }, @@ -71,7 +68,7 @@ public async Task Create_Works(IAnthropicClient client) }, ], Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, - OutputConfig = new() { Effort = Messages::Effort.Low }, + OutputConfig = new() { Effort = Effort.Low }, OutputFormat = new() { Schema = new Dictionary() @@ -79,18 +76,18 @@ public async Task Create_Works(IAnthropicClient client) { "foo", JsonSerializer.SerializeToElement("bar") }, }, }, - ServiceTier = ServiceTier.Auto, + ServiceTier = Batches::ServiceTier.Auto, StopSequences = ["string"], Stream = true, System = new( [ - new Models.Beta.Messages.BetaTextBlockParam() + new BetaTextBlockParam() { Text = "Today's date is 2024-06-01.", - CacheControl = new() { TTL = Messages::TTL.TTL5m }, + CacheControl = new() { TTL = TTL.TTL5m }, Citations = [ - new Messages::BetaCitationCharLocationParam() + new BetaCitationCharLocationParam() { CitedText = "cited_text", DocumentIndex = 0, @@ -103,14 +100,11 @@ public async Task Create_Works(IAnthropicClient client) ] ), Temperature = 1, - Thinking = new Messages::BetaThinkingConfigEnabled(1024), - ToolChoice = new Messages::BetaToolChoiceAuto() - { - DisableParallelToolUse = true, - }, + Thinking = new BetaThinkingConfigEnabled(1024), + ToolChoice = new BetaToolChoiceAuto() { DisableParallelToolUse = true }, Tools = [ - new Messages::BetaTool() + new BetaTool() { InputSchema = new() { @@ -125,8 +119,8 @@ public async Task Create_Works(IAnthropicClient client) Required = ["location"], }, Name = "name", - AllowedCallers = [Messages::AllowedCaller2.Direct], - CacheControl = new() { TTL = Messages::TTL.TTL5m }, + AllowedCallers = [BetaToolAllowedCaller.Direct], + CacheControl = new() { TTL = TTL.TTL5m }, DeferLoading = true, Description = "Get the current weather in a given location", InputExamples = @@ -137,7 +131,7 @@ public async Task Create_Works(IAnthropicClient client) }, ], Strict = true, - Type = Messages::BetaToolType.Custom, + Type = BetaToolType.Custom, }, ], TopK = 5, diff --git a/src/Anthropic.Tests/Services/Messages/BatchServiceTest.cs b/src/Anthropic.Tests/Services/Messages/BatchServiceTest.cs index 3101f051..a3e9fe2d 100644 --- a/src/Anthropic.Tests/Services/Messages/BatchServiceTest.cs +++ b/src/Anthropic.Tests/Services/Messages/BatchServiceTest.cs @@ -28,11 +28,7 @@ public async Task Create_Works(IAnthropicClient client, string modelName) MaxTokens = 1024, Messages = [ - new() - { - Content = "Hello, world", - Role = Models.Messages.Role.User, - }, + new() { Content = "Hello, world", Role = Messages::Role.User }, ], Model = modelName, Metadata = new() { UserID = "13803d75-b4b5-4c3e-b2a2-6f21399b021b" }, @@ -41,7 +37,7 @@ public async Task Create_Works(IAnthropicClient client, string modelName) Stream = true, System = new( [ - new Models.Messages.TextBlockParam() + new Messages::TextBlockParam() { Text = "Today's date is 2024-06-01.", CacheControl = new() { TTL = Messages::TTL.TTL5m }, diff --git a/src/Anthropic.Tests/TestBase.cs b/src/Anthropic.Tests/TestBase.cs new file mode 100644 index 00000000..d9e85d74 --- /dev/null +++ b/src/Anthropic.Tests/TestBase.cs @@ -0,0 +1,23 @@ +using System; + +namespace Anthropic.Tests; + +/// +/// This is the TestBase compat used as an intermediary solution until multiple providers can be supported via codegen. +/// +public abstract class TestBase +{ + protected IAnthropicClient client; + + /// + /// This class is only used by codegen tests and should not be used for hand written tests. Use the instead. + /// + public TestBase() + { + client = new AnthropicClient() + { + BaseUrl = new Uri(AnthropicTestClientsAttribute.DataServiceUrl), + APIKey = AnthropicTestClientsAttribute.ApiKey, + }; + } +} diff --git a/src/Anthropic/Anthropic.csproj b/src/Anthropic/Anthropic.csproj index c09415fb..84d26e38 100644 --- a/src/Anthropic/Anthropic.csproj +++ b/src/Anthropic/Anthropic.csproj @@ -4,7 +4,7 @@ Anthropic C# Anthropic Anthropic - 11.0.0 + 12.0.0 Anthropic Anthropic The official .NET library for the Anthropic API. @@ -43,11 +43,13 @@ + + - + \ No newline at end of file diff --git a/src/Anthropic/AnthropicClient.cs b/src/Anthropic/AnthropicClient.cs index 13a54a12..03c7787c 100644 --- a/src/Anthropic/AnthropicClient.cs +++ b/src/Anthropic/AnthropicClient.cs @@ -104,18 +104,14 @@ public async Task Execute( where T : ParamsBase { var maxRetries = this.MaxRetries ?? ClientOptions.DefaultMaxRetries; - if (maxRetries <= 0) - { - return await ExecuteOnce(request, cancellationToken).ConfigureAwait(false); - } - var retries = 0; while (true) { HttpResponse? response = null; try { - response = await ExecuteOnce(request, cancellationToken).ConfigureAwait(false); + response = await ExecuteOnce(request, retries, cancellationToken) + .ConfigureAwait(false); } catch (Exception e) { @@ -177,6 +173,7 @@ CancellationToken cancellationToken async Task ExecuteOnce( HttpRequest request, + int retryCount, CancellationToken cancellationToken = default ) where T : ParamsBase @@ -189,6 +186,10 @@ async Task ExecuteOnce( Content = request.Params.BodyContent(), }; request.Params.AddHeadersToRequest(requestMessage, this._options); + if (!requestMessage.Headers.Contains("x-stainless-retry-count")) + { + requestMessage.Headers.Add("x-stainless-retry-count", retryCount.ToString()); + } using CancellationTokenSource timeoutCts = new( this.Timeout ?? ClientOptions.DefaultTimeout ); diff --git a/src/Anthropic/AnthropicClientExtensions.cs b/src/Anthropic/AnthropicClientExtensions.cs index b1bcfef2..a7fb6228 100644 --- a/src/Anthropic/AnthropicClientExtensions.cs +++ b/src/Anthropic/AnthropicClientExtensions.cs @@ -357,6 +357,8 @@ out StreamingFunctionData? functionData ) ); } + + streamingFunctions.Clear(); } break; } diff --git a/src/Anthropic/CHANGELOG.md b/src/Anthropic/CHANGELOG.md new file mode 100644 index 00000000..6ca04ccb --- /dev/null +++ b/src/Anthropic/CHANGELOG.md @@ -0,0 +1,130 @@ +# Changelog + +## 12.0.0 (2025-12-10) + +Full Changelog: [Anthropic-v11.0.0...Anthropic-v12.0.0](https://github.com/anthropics/anthropic-sdk-csharp/compare/Anthropic-v11.0.0...Anthropic-v12.0.0) + +### ⚠ BREAKING CHANGES + +* **client:** use readonly types for properties + +### Features + +* add Foundry client ([5f87e12](https://github.com/anthropics/anthropic-sdk-csharp/commit/5f87e129a262d8a373e5e10bcca4196cf5db0394)) +* **api:** add claude-opus-4-1-20250805 ([c38689c](https://github.com/anthropics/anthropic-sdk-csharp/commit/c38689ce56b61bd5259785cd0478c8cecdf01630)) +* **api:** add support for Search Result Content Blocks ([3300718](https://github.com/anthropics/anthropic-sdk-csharp/commit/33007185312999c941e9ece33dde30b397e1b2ec)) +* **api:** add support for structured outputs beta ([a809be6](https://github.com/anthropics/anthropic-sdk-csharp/commit/a809be6a3bddca622662670044c480ecdfec83eb)) +* **api:** adds support for Claude Opus 4.5, Effort, Advance Tool Use Features, Autocompaction, and Computer Use v5 ([144a820](https://github.com/anthropics/anthropic-sdk-csharp/commit/144a8209e522f5bba2174b1efd3d5607a2d7c145)) +* **api:** adds support for Documents in tool results ([a7b5086](https://github.com/anthropics/anthropic-sdk-csharp/commit/a7b5086b8dd0211e723b4d6f9b903091df387d37)) +* **api:** adds support for text_editor_20250728 tool ([159d728](https://github.com/anthropics/anthropic-sdk-csharp/commit/159d7280cc3347b2241833ec32e64ddd8d467fbf)) +* **api:** adds support for web_fetch_20250910 tool ([1d12859](https://github.com/anthropics/anthropic-sdk-csharp/commit/1d128598434a110447606a22c69394f9e24262d5)) +* **api:** makes 1 hour TTL Cache Control generally available ([84b1ad3](https://github.com/anthropics/anthropic-sdk-csharp/commit/84b1ad3530ecf8f6fdb3c6dcd12e9a6331add9b4)) +* **api:** removed older deprecated models ([f5aafba](https://github.com/anthropics/anthropic-sdk-csharp/commit/f5aafbabd37dce4c3d14e3a8925bd9fde926bbd3)) +* **api:** rename C# package to Anthropic ([83b024f](https://github.com/anthropics/anthropic-sdk-csharp/commit/83b024f68676a9a244650172ec46352814fe3669)) +* **api:** search result content blocks ([e4368ee](https://github.com/anthropics/anthropic-sdk-csharp/commit/e4368ee1df5de9963ecd5295db7adaa2f882b776)) +* **api:** update PHP and C# ([d63878a](https://github.com/anthropics/anthropic-sdk-csharp/commit/d63878a830159b05ad5262de680cbd3c1cd1dd99)) +* **api:** update to desired NuGet name ([c4b6820](https://github.com/anthropics/anthropic-sdk-csharp/commit/c4b682000227c3daf1b6c854f7b4b3fe316aec45)) +* **betas:** add context-1m-2025-08-07 ([f65802a](https://github.com/anthropics/anthropic-sdk-csharp/commit/f65802a33c9474d32774a4aabae84ff53403acf8)) +* **ci:** add publishing flow for nuget ([487ac2e](https://github.com/anthropics/anthropic-sdk-csharp/commit/487ac2e31527626cf2105bb3209faa49ddb1654a)) +* **client:** add implicit conversions to enums ([324f263](https://github.com/anthropics/anthropic-sdk-csharp/commit/324f263ccdee745b3f815abb17c09310146e56c0)) +* **client:** add some convenience constructors ([e2541e1](https://github.com/anthropics/anthropic-sdk-csharp/commit/e2541e10315a9304f4925fdafffc2494ab62a20f)) +* **client:** add streaming methods ([b394064](https://github.com/anthropics/anthropic-sdk-csharp/commit/b394064caef025f0a8cacfc299dc1dbe9636b1c8)) +* **client:** add switch and match helpers for unions ([d44a80c](https://github.com/anthropics/anthropic-sdk-csharp/commit/d44a80c8872f1fca137fbbfb4ed41c178ebe3c35)) +* **client:** add x-stainless-retry-count ([ad0fba4](https://github.com/anthropics/anthropic-sdk-csharp/commit/ad0fba4c807bed061f3a79d39d12572fd6668452)) +* **client:** additional methods for positional params ([08c27c6](https://github.com/anthropics/anthropic-sdk-csharp/commit/08c27c6a4cb45b886be44babbb51bf4934add374)) +* **client:** additional methods for positional params ([8bc6323](https://github.com/anthropics/anthropic-sdk-csharp/commit/8bc6323c38ce551f995bec5e4b1584460b7f037b)) +* **client:** adds support for code-execution-2025-08-26 tool ([5be3c78](https://github.com/anthropics/anthropic-sdk-csharp/commit/5be3c787f331d2dcaae55f1ed900b6cc04052818)) +* **client:** allow omitting all params object when all optional ([68a792f](https://github.com/anthropics/anthropic-sdk-csharp/commit/68a792f6591d02d8fce140949831a84b21eed686)) +* **client:** automatically set constants for user ([bb1343e](https://github.com/anthropics/anthropic-sdk-csharp/commit/bb1343ef5311c535a0836e83c65e156483eb4a45)) +* **client:** basic paginated endpoint support ([4766f1e](https://github.com/anthropics/anthropic-sdk-csharp/commit/4766f1ec369b01863ce96a22264f40d9f953f412)) +* **client:** implement implicit union casts ([e36b8fa](https://github.com/anthropics/anthropic-sdk-csharp/commit/e36b8fa372c81c387298bd2e700a74a0dac2c8d1)) +* **client:** improve csproj ([0874d78](https://github.com/anthropics/anthropic-sdk-csharp/commit/0874d78b4d9418277b0912f88f251154c5cef3e5)) +* **client:** improve model names ([18a0af9](https://github.com/anthropics/anthropic-sdk-csharp/commit/18a0af9f5d5eca5e0b1267c213e35d748ca3a0a0)) +* **client:** improve signature of `trypickx` methods ([620b39b](https://github.com/anthropics/anthropic-sdk-csharp/commit/620b39bd653c5c5fbdf3ddd0d8bfe3921ec9c81f)) +* **client:** improve some names ([8d28ac4](https://github.com/anthropics/anthropic-sdk-csharp/commit/8d28ac49a9a77b1486607c4fd4ddcfb40a138a3c)) +* **client:** make union deserialization more robust ([26d42da](https://github.com/anthropics/anthropic-sdk-csharp/commit/26d42dae0039f709e4ca33449c9567bbc0ff689b)) +* **client:** make union deserialization more robust ([f85bc36](https://github.com/anthropics/anthropic-sdk-csharp/commit/f85bc367ad3f076d36b233cc956768fea226d1ae)) +* **client:** shorten union variant names ([c397c9b](https://github.com/anthropics/anthropic-sdk-csharp/commit/c397c9bda8cfde000e9b092fb0f384695a9993cd)) +* **internal:** allow overriding mock url via `TEST_API_BASE_URL` env ([f14a23c](https://github.com/anthropics/anthropic-sdk-csharp/commit/f14a23c5b6065a377bf273189c5cf4d5b1826250)) + + +### Bug Fixes + +* **client:** better type names ([057bf2d](https://github.com/anthropics/anthropic-sdk-csharp/commit/057bf2ddf817d443f86fe5913cf5399705c65914)) +* **client:** check response status when `MaxRetries = 0` ([6e568ec](https://github.com/anthropics/anthropic-sdk-csharp/commit/6e568ec525ca23e933660c6fec61fc81c27f9f7c)) +* **client:** compilation error ([56d1c41](https://github.com/anthropics/anthropic-sdk-csharp/commit/56d1c41dbcca95ddbd40cb296ebe516a3598b30d)) +* **client:** handle multiple auth options gracefully ([a5fdd62](https://github.com/anthropics/anthropic-sdk-csharp/commit/a5fdd6218b188cb45e9a10304edd40334261d272)) +* **client:** handling of null value type ([eb6a775](https://github.com/anthropics/anthropic-sdk-csharp/commit/eb6a775164392f1a55bdfecee3ac402b5a0fdd0a)) +* **client:** improve model validation ([b77753e](https://github.com/anthropics/anthropic-sdk-csharp/commit/b77753e46cad3eda6ef37f4ad2df2066199b1a14)) +* **client:** return correct type for foundry#WithOptions ([#18](https://github.com/anthropics/anthropic-sdk-csharp/issues/18)) ([9ff2124](https://github.com/anthropics/anthropic-sdk-csharp/commit/9ff2124a9190269ff4a469b6e8c9f6b895f8d2d2)) +* **client:** return correct type for foundry#WithOptions ([#18](https://github.com/anthropics/anthropic-sdk-csharp/issues/18)) ([f814a46](https://github.com/anthropics/anthropic-sdk-csharp/commit/f814a460503abf7fdf7a824b5bf446ef74d60f28)) +* **client:** support non-optional client options ([fadaa63](https://github.com/anthropics/anthropic-sdk-csharp/commit/fadaa63599a9411094aede97aa59084916a3de6d)) +* **client:** update custom code for readonly ([#198](https://github.com/anthropics/anthropic-sdk-csharp/issues/198)) ([e3c26f1](https://github.com/anthropics/anthropic-sdk-csharp/commit/e3c26f1fb586a8a4de5df1cd08618d73b36006f0)) +* **client:** use readonly types for properties ([cd28fd5](https://github.com/anthropics/anthropic-sdk-csharp/commit/cd28fd566402011eed8f369bcc9173119cb1b262)) +* **client:** with expressions for models ([b42ce94](https://github.com/anthropics/anthropic-sdk-csharp/commit/b42ce9405f04d3f830c2e4bfdeb9c433ba780222)) +* **docs:** re-order using statements ([b77bdb2](https://github.com/anthropics/anthropic-sdk-csharp/commit/b77bdb2aa4bcde1a0e21938c1d4be5ea755dfaed)) +* **internal:** don't format csproj files ([0b5c2c6](https://github.com/anthropics/anthropic-sdk-csharp/commit/0b5c2c660f8a2882034c6a96dd88ba7b2c98d6e8)) +* **internal:** minor project fixes ([3c344e2](https://github.com/anthropics/anthropic-sdk-csharp/commit/3c344e2db929ed43cc49854c791ea10e5e42489c)) +* **internal:** prefer to use implicit instantiation when possible ([b869753](https://github.com/anthropics/anthropic-sdk-csharp/commit/b86975337839d95e151e27421c84566ad0c6ecd7)) +* **internal:** remove unused null class ([c46f844](https://github.com/anthropics/anthropic-sdk-csharp/commit/c46f844118f54ca85615794d420c8b4202761f27)) +* **internal:** various minor code fixes ([136162a](https://github.com/anthropics/anthropic-sdk-csharp/commit/136162addc0812087d051e8e5844226f31eda895)) +* remove bad preprocessor directive ([9420cfd](https://github.com/anthropics/anthropic-sdk-csharp/commit/9420cfd8cb741c0e5c79491e04ed4ea6df284f52)) +* use correct header name ([c83471e](https://github.com/anthropics/anthropic-sdk-csharp/commit/c83471e37ec40cc70b5fccc5f125f731353699be)) +* use correct version ([aeba41c](https://github.com/anthropics/anthropic-sdk-csharp/commit/aeba41c844ba58fe59a56090dd78fd794ad07a8b)) +* use correct versions ([7c97d7f](https://github.com/anthropics/anthropic-sdk-csharp/commit/7c97d7f19c6937a2dacb666b05b9b9d040d677c7)) +* use correct versions ([c78c8db](https://github.com/anthropics/anthropic-sdk-csharp/commit/c78c8db4b6effa6b1438bb879bcafdad2d155808)) + + +### Performance Improvements + +* **client:** use async deserialization in `HttpResponse` ([293020b](https://github.com/anthropics/anthropic-sdk-csharp/commit/293020b5e84414b751218f0c157ab49e9fb44980)) + + +### Chores + +* **api:** remove unsupported endpoints ([d318ba7](https://github.com/anthropics/anthropic-sdk-csharp/commit/d318ba7c3c652b813fe81316ac5d5110fd8ebcb2)) +* **api:** update BetaCitationSearchResultLocation ([801a222](https://github.com/anthropics/anthropic-sdk-csharp/commit/801a222c8eeaa43625bdc078ef9da8ffec9351e4)) +* **client:** add TextEditor_20250429 tool ([adee5b4](https://github.com/anthropics/anthropic-sdk-csharp/commit/adee5b42af4ac04e3569570aca45a931aa16dd6f)) +* **client:** change name of underlying properties for models and params ([75a2cce](https://github.com/anthropics/anthropic-sdk-csharp/commit/75a2ccecefaf3fff5a07138a3c38ff0b9b9df476)) +* **client:** deprecate some symbols ([08bfad9](https://github.com/anthropics/anthropic-sdk-csharp/commit/08bfad97735fda235d92655adae05be45d51eac0)) +* **client:** improve union validation ([d86c38d](https://github.com/anthropics/anthropic-sdk-csharp/commit/d86c38d5ab783c07b67f95c581d44e644f48b0d2)) +* **client:** make some interfaces internal ([476e69e](https://github.com/anthropics/anthropic-sdk-csharp/commit/476e69e077869ce56271dfe69837a02ea1d66811)) +* **client:** swap `[@params](https://github.com/params)` to better name ([3d8e0d9](https://github.com/anthropics/anthropic-sdk-csharp/commit/3d8e0d96ba2e7e6d1c2aaf4da3848647bd6d5e1f)) +* **client:** update namespace imports ([764df51](https://github.com/anthropics/anthropic-sdk-csharp/commit/764df5100097db98afeac71075e94eb84d4f5572)) +* fix ci ([#196](https://github.com/anthropics/anthropic-sdk-csharp/issues/196)) ([8dede61](https://github.com/anthropics/anthropic-sdk-csharp/commit/8dede6176cb86e1ae85db9c8d0fae50c595ef964)) +* **internal:** add logo to nuget package ([#181](https://github.com/anthropics/anthropic-sdk-csharp/issues/181)) ([e01f08d](https://github.com/anthropics/anthropic-sdk-csharp/commit/e01f08dbd35f05c3ecc964eb040312b4f7ca6713)) +* **internal:** add tests for constants ([25b6f4f](https://github.com/anthropics/anthropic-sdk-csharp/commit/25b6f4f526fdc2b268ac850f2d73cdb5d39cb685)) +* **internal:** clean up diffs vs codegen ([53b2d3c](https://github.com/anthropics/anthropic-sdk-csharp/commit/53b2d3cd5cc2d852deceba162f1482f0013af05b)) +* **internal:** codegen related update ([fb6b738](https://github.com/anthropics/anthropic-sdk-csharp/commit/fb6b7383219e9fef56cdf0786170f1943249b9c7)) +* **internal:** codegen related update ([135523a](https://github.com/anthropics/anthropic-sdk-csharp/commit/135523aad5f9df5ee22a25f4ba7670335f2b8647)) +* **internal:** equality and more unit tests ([f270a7e](https://github.com/anthropics/anthropic-sdk-csharp/commit/f270a7ecbef5fb86d1193b48ae957ac1f3b4f563)) +* **internal:** refactor tests to de-duplicate client instantiation logic ([f14a23c](https://github.com/anthropics/anthropic-sdk-csharp/commit/f14a23c5b6065a377bf273189c5cf4d5b1826250)) +* **internal:** remove redundant keyword ([72e07e7](https://github.com/anthropics/anthropic-sdk-csharp/commit/72e07e7e8de33aa73203afa64d91ec6860a98283)) +* **internal:** remove unnecessary internal aliasing ([d210122](https://github.com/anthropics/anthropic-sdk-csharp/commit/d2101221fc498b57c60593896491751a6c77f9d8)) +* **internal:** rename parameters ([0013847](https://github.com/anthropics/anthropic-sdk-csharp/commit/0013847d2d7db6f4611b6c863f74b11a442310a1)) +* **internal:** stop running whitespace lint ([f14a23c](https://github.com/anthropics/anthropic-sdk-csharp/commit/f14a23c5b6065a377bf273189c5cf4d5b1826250)) +* **internal:** suppress diagnostic for .netstandard2.0 ([9ede62d](https://github.com/anthropics/anthropic-sdk-csharp/commit/9ede62de370abcad1fc1a5211700a6c967d360ca)) +* **internal:** suppress diagnostic for .netstandard2.0 ([1b0714d](https://github.com/anthropics/anthropic-sdk-csharp/commit/1b0714dc78ba2e69ab149d7cf768963379ec73e5)) +* **internal:** update csproj formatting ([6036c7f](https://github.com/anthropics/anthropic-sdk-csharp/commit/6036c7fa2683bc18299fa6d994b4cd117988d86a)) +* **internal:** use nicer generic names ([00c3c7e](https://github.com/anthropics/anthropic-sdk-csharp/commit/00c3c7e215233ff0882930db8dc8177c22b85165)) +* update formatting ([8b06f4f](https://github.com/anthropics/anthropic-sdk-csharp/commit/8b06f4f14153b608acbe1f00461a055e3c74d553)) +* use non-aliased `using` ([ba9d1ac](https://github.com/anthropics/anthropic-sdk-csharp/commit/ba9d1ac2f5b3e86dc4fcf9f5857e550a40ec8995)) + + +### Documentation + +* add more comments ([8ade211](https://github.com/anthropics/anthropic-sdk-csharp/commit/8ade21175fb18a01e79a8393e49ee163c50e9e94)) +* add more comments ([915d808](https://github.com/anthropics/anthropic-sdk-csharp/commit/915d80832dc1e11b212048081ce55255fe5b1024)) +* **client:** add more property comments ([a3e973b](https://github.com/anthropics/anthropic-sdk-csharp/commit/a3e973b0e6d057e58e6f0bd08c8a5635da896974)) +* **internal:** add warning about implementing interface ([2171969](https://github.com/anthropics/anthropic-sdk-csharp/commit/217196968fa67df4ef967333c1e0ed423d4fe1e6)) + + +### Refactors + +* **client:** make unknown variants implicit ([7b966ab](https://github.com/anthropics/anthropic-sdk-csharp/commit/7b966ab3dbfd1d41998fb0ab71f8f1ae9e0d625a)) +* **client:** make unknown variants implicit ([eb0e5b6](https://github.com/anthropics/anthropic-sdk-csharp/commit/eb0e5b628d7090adc34300775043ecd26ccfffaf)) +* **client:** refine enum representation ([a3e973b](https://github.com/anthropics/anthropic-sdk-csharp/commit/a3e973b0e6d057e58e6f0bd08c8a5635da896974)) +* **client:** use `System.Net.ServerSentEvents` ([b733f32](https://github.com/anthropics/anthropic-sdk-csharp/commit/b733f32912e9b5a0ff1bd90c9a56de8ba14950a2)) +* **client:** use plural for service namespace ([843da53](https://github.com/anthropics/anthropic-sdk-csharp/commit/843da53c91a4e925298aae8907f8990b7e13de9e)) +* **internal:** remove abstract static methods ([a1e13bb](https://github.com/anthropics/anthropic-sdk-csharp/commit/a1e13bbf38dfa84858fe31e9418d80fe1284bebb)) +* **internal:** share get/set logic ([eb6a775](https://github.com/anthropics/anthropic-sdk-csharp/commit/eb6a775164392f1a55bdfecee3ac402b5a0fdd0a)) diff --git a/src/Anthropic/Core/ApiEnum.cs b/src/Anthropic/Core/ApiEnum.cs index 8b5152da..ae479187 100644 --- a/src/Anthropic/Core/ApiEnum.cs +++ b/src/Anthropic/Core/ApiEnum.cs @@ -21,7 +21,7 @@ namespace Anthropic.Core; /// unaware of. /// /// -public record struct ApiEnum(JsonElement Json) +public record class ApiEnum(JsonElement Json) where TEnum : struct, Enum { /// @@ -36,7 +36,7 @@ public record struct ApiEnum(JsonElement Json) /// to access the raw value. /// /// - public readonly TRaw Raw() => + public TRaw Raw() => JsonSerializer.Deserialize(this.Json, ModelBase.SerializerOptions) ?? throw new AnthropicInvalidDataException( string.Format("{0} cannot be null", nameof(this.Json)) @@ -48,7 +48,7 @@ public readonly TRaw Raw() => /// /// Use to access the raw value.. /// - public readonly TEnum Value() => + public TEnum Value() => JsonSerializer.Deserialize(this.Json, ModelBase.SerializerOptions); /// @@ -58,7 +58,7 @@ public readonly TEnum Value() => /// Thrown when this instance's raw value isn't a member of . /// /// - public readonly void Validate() + public void Validate() { if (!Enum.IsDefined(typeof(TEnum), Value())) { @@ -66,6 +66,16 @@ public readonly void Validate() } } + public virtual bool Equals(ApiEnum? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } + public static implicit operator TRaw(ApiEnum value) => value.Raw(); public static implicit operator TEnum(ApiEnum value) => value.Value(); diff --git a/src/Anthropic/Core/ModelBase.cs b/src/Anthropic/Core/ModelBase.cs index cb6f8cec..330ae5a2 100644 --- a/src/Anthropic/Core/ModelBase.cs +++ b/src/Anthropic/Core/ModelBase.cs @@ -1,17 +1,31 @@ using System.Collections.Generic; using System.Text.Json; +using Anthropic.Exceptions; using Anthropic.Models.Beta; using Anthropic.Models.Beta.Files; using Anthropic.Models.Messages.Batches; using Batches = Anthropic.Models.Beta.Messages.Batches; -using Messages = Anthropic.Models.Messages; +using Messages = Anthropic.Models.Beta.Messages; namespace Anthropic.Core; +/// +/// The base class for all API objects with properties. +/// +/// API objects such as enums and unions do not inherit from this class. +/// public abstract record class ModelBase { private protected FreezableDictionary _rawData = []; + protected ModelBase(ModelBase modelBase) + { + this._rawData = [.. modelBase._rawData]; + } + + /// + /// The backing JSON properties of the instance. + /// public IReadOnlyDictionary RawData { get { return this._rawData.Freeze(); } @@ -21,106 +35,76 @@ public IReadOnlyDictionary RawData { Converters = { - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter< - string, - global::Anthropic.Models.Beta.Messages.BetaBashCodeExecutionToolResultErrorParamErrorCode - >(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter< - string, - global::Anthropic.Models.Beta.Messages.AllowedCallerModel - >(), - new ApiEnumConverter< - string, - global::Anthropic.Models.Beta.Messages.BetaCodeExecutionToolResultErrorCode - >(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), new ApiEnumConverter< string, - global::Anthropic.Models.Beta.Messages.BetaServerToolUseBlockParamName - >(), - new ApiEnumConverter(), - new ApiEnumConverter< - string, - global::Anthropic.Models.Beta.Messages.BetaSkillParamsType - >(), - new ApiEnumConverter(), - new ApiEnumConverter< - string, - global::Anthropic.Models.Beta.Messages.BetaTextEditorCodeExecutionToolResultErrorErrorCode - >(), - new ApiEnumConverter< - string, - global::Anthropic.Models.Beta.Messages.BetaTextEditorCodeExecutionToolResultErrorParamErrorCode - >(), - new ApiEnumConverter(), - new ApiEnumConverter< - string, - global::Anthropic.Models.Beta.Messages.BetaTextEditorCodeExecutionViewResultBlockParamFileType - >(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter< - string, - global::Anthropic.Models.Beta.Messages.BetaToolSearchToolBm25_20251119Type - >(), - new ApiEnumConverter(), - new ApiEnumConverter< - string, - global::Anthropic.Models.Beta.Messages.BetaToolSearchToolRegex20251119Type - >(), - new ApiEnumConverter(), - new ApiEnumConverter< - string, - global::Anthropic.Models.Beta.Messages.BetaToolSearchToolResultErrorErrorCode + global::Anthropic.Models.Messages.WebSearchToolResultErrorErrorCode >(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), new ApiEnumConverter< string, - global::Anthropic.Models.Beta.Messages.BetaToolSearchToolResultErrorParamErrorCode + Messages::BetaBashCodeExecutionToolResultErrorParamErrorCode >(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), - new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), new ApiEnumConverter< string, - global::Anthropic.Models.Beta.Messages.BetaUsageServiceTier + Messages::BetaTextEditorCodeExecutionToolResultErrorErrorCode >(), - new ApiEnumConverter(), new ApiEnumConverter< string, - global::Anthropic.Models.Beta.Messages.BetaWebFetchToolResultErrorCode + Messages::BetaTextEditorCodeExecutionToolResultErrorParamErrorCode >(), - new ApiEnumConverter(), + new ApiEnumConverter(), new ApiEnumConverter< string, - global::Anthropic.Models.Beta.Messages.BetaWebSearchToolResultErrorCode + Messages::BetaTextEditorCodeExecutionViewResultBlockParamFileType >(), - new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), + new ApiEnumConverter(), new ApiEnumConverter(), new ApiEnumConverter(), new ApiEnumConverter(), @@ -132,11 +116,151 @@ public IReadOnlyDictionary RawData WriteIndented = true, }; + internal static void Set(IDictionary dictionary, string key, T value) + { + dictionary[key] = JsonSerializer.SerializeToElement(value, SerializerOptions); + } + + internal static T GetNotNullClass( + IReadOnlyDictionary dictionary, + string key + ) + where T : class + { + if (!dictionary.TryGetValue(key, out JsonElement element)) + { + throw new AnthropicInvalidDataException($"'{key}' cannot be absent"); + } + + try + { + return JsonSerializer.Deserialize(element, SerializerOptions) + ?? throw new AnthropicInvalidDataException($"'{key}' cannot be null"); + } + catch (JsonException e) + { + throw new AnthropicInvalidDataException( + $"'{key}' must be of type {typeof(T).FullName}", + e + ); + } + } + + internal static T GetNotNullStruct( + IReadOnlyDictionary dictionary, + string key + ) + where T : struct + { + if (!dictionary.TryGetValue(key, out JsonElement element)) + { + throw new AnthropicInvalidDataException($"'{key}' cannot be absent"); + } + + try + { + return JsonSerializer.Deserialize(element, SerializerOptions) + ?? throw new AnthropicInvalidDataException($"'{key}' cannot be null"); + } + catch (JsonException e) + { + throw new AnthropicInvalidDataException( + $"'{key}' must be of type {typeof(T).FullName}", + e + ); + } + } + + internal static T? GetNullableClass( + IReadOnlyDictionary dictionary, + string key + ) + where T : class + { + if (!dictionary.TryGetValue(key, out JsonElement element)) + { + return null; + } + + try + { + return JsonSerializer.Deserialize(element, SerializerOptions); + } + catch (JsonException e) + { + throw new AnthropicInvalidDataException( + $"'{key}' must be of type {typeof(T).FullName}", + e + ); + } + } + + internal static T? GetNullableStruct( + IReadOnlyDictionary dictionary, + string key + ) + where T : struct + { + if (!dictionary.TryGetValue(key, out JsonElement element)) + { + return null; + } + + try + { + return JsonSerializer.Deserialize(element, SerializerOptions); + } + catch (JsonException e) + { + throw new AnthropicInvalidDataException( + $"'{key}' must be of type {typeof(T).FullName}", + e + ); + } + } + public sealed override string? ToString() { return JsonSerializer.Serialize(this.RawData, _toStringSerializerOptions); } + public virtual bool Equals(ModelBase? other) + { + if (other == null || this.RawData.Count != other.RawData.Count) + { + return false; + } + + foreach (var item in this.RawData) + { + if (!other.RawData.TryGetValue(item.Key, out var otherValue)) + { + return false; + } + + if (!JsonElement.DeepEquals(item.Value, otherValue)) + { + return false; + } + } + + return true; + } + + public override int GetHashCode() + { + return 0; + } + + /// + /// Validates that all required fields are set and that each field's value is of the expected type. + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public abstract void Validate(); } @@ -144,13 +268,21 @@ public IReadOnlyDictionary RawData /// NOTE: Do not inherit from this type outside the SDK unless you're okay with breaking /// changes in non-major versions. We may add new methods in the future that cause /// existing derived classes to break. +/// +/// NOTE: This interface is in the style of a factory instance instead of using +/// abstract static methods because .NET Standard 2.0 doesn't support abstract static methods. /// interface IFromRaw { /// - /// NOTE: This interface is in the style of a factory instance instead of using - /// abstract static methods because .NET Standard 2.0 doesn't support abstract - /// static methods. + /// Returns an instance constructed from the given raw JSON properties. + /// + /// Required field and type mismatches are not checked. In these cases accessing + /// the relevant properties of the constructed instance may throw. + /// + /// This method is useful for constructing an instance from already serialized + /// data or for sending arbitrary data to the API (e.g. for undocumented or not + /// yet supported properties or values). /// T FromRawUnchecked(IReadOnlyDictionary rawData); } diff --git a/src/Anthropic/Core/ParamsBase.cs b/src/Anthropic/Core/ParamsBase.cs index 104c96fe..4864caeb 100644 --- a/src/Anthropic/Core/ParamsBase.cs +++ b/src/Anthropic/Core/ParamsBase.cs @@ -13,12 +13,12 @@ namespace Anthropic.Core; public abstract record class ParamsBase { - static readonly IReadOnlyDictionary s_defaultHeaders; + static readonly IReadOnlyDictionary defaultHeaders; static ParamsBase() { var runtime = GetRuntime(); - s_defaultHeaders = new Dictionary + defaultHeaders = new Dictionary { ["User-Agent"] = GetUserAgent(), ["X-Stainless-Arch"] = GetOSArch(), @@ -33,13 +33,19 @@ static ParamsBase() private protected FreezableDictionary _rawQueryData = []; + private protected FreezableDictionary _rawHeaderData = []; + + protected ParamsBase(ParamsBase paramsBase) + { + this._rawHeaderData = [.. paramsBase._rawHeaderData]; + this._rawQueryData = [.. paramsBase._rawQueryData]; + } + public IReadOnlyDictionary RawQueryData { get { return this._rawQueryData.Freeze(); } } - private protected FreezableDictionary _rawHeaderData = []; - public IReadOnlyDictionary RawHeaderData { get { return this._rawHeaderData.Freeze(); } @@ -186,7 +192,7 @@ protected string QueryString(ClientOptions options) protected static void AddDefaultHeaders(HttpRequestMessage request, ClientOptions options) { - foreach (var header in s_defaultHeaders) + foreach (var header in defaultHeaders) { request.Headers.Add(header.Key, header.Value); } diff --git a/src/Anthropic/Core/Sse.cs b/src/Anthropic/Core/Sse.cs new file mode 100644 index 00000000..5a5133b4 --- /dev/null +++ b/src/Anthropic/Core/Sse.cs @@ -0,0 +1,49 @@ +using System.Collections.Generic; +using System.Net.Http; +using System.Net.ServerSentEvents; +using System.Runtime.CompilerServices; +using System.Text.Json; +using System.Threading; +using Anthropic.Exceptions; + +namespace Anthropic.Core; + +static class Sse +{ + internal static async IAsyncEnumerable Enumerate( + HttpResponseMessage response, + [EnumeratorCancellation] CancellationToken cancellationToken = default + ) + { + using var stream = await response + .Content.ReadAsStreamAsync( +#if NET + cancellationToken +#endif + ) + .ConfigureAwait(false); + + await foreach (var item in SseParser.Create(stream).EnumerateAsync(cancellationToken)) + { + switch (item.EventType) + { + case "completion": + case "message_start": + case "message_delta": + case "message_stop": + case "content_block_start": + case "content_block_delta": + case "content_block_stop": + yield return JsonSerializer.Deserialize(item.Data) + ?? throw new AnthropicInvalidDataException("Message cannot be null"); + break; + case "ping": + continue; + case "error": + throw new AnthropicSseException( + string.Format("SSE error returned from server: '{0}'", item.Data) + ); + } + } + } +} diff --git a/src/Anthropic/Core/SseMessage.cs b/src/Anthropic/Core/SseMessage.cs deleted file mode 100644 index 6e947580..00000000 --- a/src/Anthropic/Core/SseMessage.cs +++ /dev/null @@ -1,86 +0,0 @@ -using System.Collections.Generic; -using System.IO; -using System.Net.Http; -using System.Runtime.CompilerServices; -using System.Text.Json; -using System.Threading; -using Anthropic.Exceptions; - -namespace Anthropic.Core; - -sealed record class SseMessage(string? Event, string Data, string? ID, int? Retry) -{ - internal static async IAsyncEnumerable GetEnumerable( - HttpResponseMessage response, - [EnumeratorCancellation] CancellationToken cancellationToken = default - ) - { - var state = new SseState(); - - using var stream = await response - .Content.ReadAsStreamAsync( -#if NET - cancellationToken -#endif - ) - .ConfigureAwait(false); - using var reader = new StreamReader(stream); - while (true) - { - string line; - try - { - var maybeLine = await reader.ReadLineAsync( -#if NET - cancellationToken -#endif - ).ConfigureAwait(false); - if (maybeLine == null) - { - break; - } - else - { - line = maybeLine; - } - } - catch (HttpRequestException e) - { - throw new AnthropicIOException("I/O Exception", e); - } - // Check for cancellation before decoding the line. - cancellationToken.ThrowIfCancellationRequested(); - - var message = state.Decode(line); - if (message == null) - { - continue; - } - - switch (message.Event) - { - case "completion": - case "message_start": - case "message_delta": - case "message_stop": - case "content_block_start": - case "content_block_delta": - case "content_block_stop": - yield return message; - break; - case "ping": - continue; - case "error": - throw new AnthropicSseException( - string.Format("SSE error returned from server: '{0}'", message) - ); - } - } - } - - internal T Deserialize() - { - return JsonSerializer.Deserialize(this.Data) - ?? throw new AnthropicInvalidDataException("Message cannot be null"); - } -} diff --git a/src/Anthropic/Core/SseState.cs b/src/Anthropic/Core/SseState.cs deleted file mode 100644 index c1515faa..00000000 --- a/src/Anthropic/Core/SseState.cs +++ /dev/null @@ -1,95 +0,0 @@ -using System.Collections.Generic; - -namespace Anthropic.Core; - -sealed class SseState -{ - string? _event = null; - readonly List _data = []; - string? _lastId = null; - int? _retry = null; - - // https://html.spec.whatwg.org/multipage/server-sent-events.html#event-stream-interpretation - internal SseMessage? Decode(string line) - { - if (line.Length == 0) - { - return Flush(); - } - - if (line.StartsWith(":")) - { - return null; - } - - string fieldName; - string value; - - var colonIndex = line.IndexOf(':'); - if (colonIndex == -1) - { - fieldName = line; - value = ""; - } - else - { - fieldName = line.Substring(0, colonIndex); - value = line.Substring(colonIndex + 1); - } - - if (value.StartsWith(" ")) - { - value = value.Substring(1); - } - - switch (fieldName) - { - case "event": - _event = value; - break; - case "data": - _data.Add(value); - break; - case "id": - if (!value.Contains("\u0000")) - { - _lastId = value; - } - break; - case "retry": - if (int.TryParse(value, out var result)) - { - _retry = result; - } - break; - } - - return null; - } - - SseMessage? Flush() - { - if (IsEmpty()) - { - return null; - } - - var message = new SseMessage(_event, string.Join("\n", _data), _lastId, _retry); - - // NOTE: Per the SSE spec, do not reset _lastId. - _event = null; - _data.Clear(); - _retry = null; - - return message; - } - - bool IsEmpty() => - (_event == null || _event.Length == 0) - && _data.Count == 0 - && (_lastId == null || _lastId.Length == 0) - && _retry == null; - - public override string ToString() => - string.Format("SseState: event={0}, data={1}", _event, string.Join("\n", _data)); -} diff --git a/src/Anthropic/Models/APIErrorObject.cs b/src/Anthropic/Models/APIErrorObject.cs index 2eb47184..aa95ef73 100644 --- a/src/Anthropic/Models/APIErrorObject.cs +++ b/src/Anthropic/Models/APIErrorObject.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class APIErrorObject : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public APIErrorObject() this.Type = JsonSerializer.Deserialize("\"api_error\""); } + public APIErrorObject(APIErrorObject apiErrorObject) + : base(apiErrorObject) { } + public APIErrorObject(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public APIErrorObject(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static APIErrorObject FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -107,6 +77,7 @@ public APIErrorObject(string message) class APIErrorObjectFromRaw : IFromRaw { + /// public APIErrorObject FromRawUnchecked(IReadOnlyDictionary rawData) => APIErrorObject.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/AuthenticationError.cs b/src/Anthropic/Models/AuthenticationError.cs index ea17e1b0..acf82b87 100644 --- a/src/Anthropic/Models/AuthenticationError.cs +++ b/src/Anthropic/Models/AuthenticationError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class AuthenticationError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public AuthenticationError() this.Type = JsonSerializer.Deserialize("\"authentication_error\""); } + public AuthenticationError(AuthenticationError authenticationError) + : base(authenticationError) { } + public AuthenticationError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public AuthenticationError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static AuthenticationError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public AuthenticationError(string message) class AuthenticationErrorFromRaw : IFromRaw { + /// public AuthenticationError FromRawUnchecked(IReadOnlyDictionary rawData) => AuthenticationError.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/BetaAPIError.cs b/src/Anthropic/Models/Beta/BetaAPIError.cs index a4041f89..17c19d5b 100644 --- a/src/Anthropic/Models/Beta/BetaAPIError.cs +++ b/src/Anthropic/Models/Beta/BetaAPIError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaAPIError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public BetaAPIError() this.Type = JsonSerializer.Deserialize("\"api_error\""); } + public BetaAPIError(BetaAPIError betaAPIError) + : base(betaAPIError) { } + public BetaAPIError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaAPIError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaAPIError FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -107,6 +77,7 @@ public BetaAPIError(string message) class BetaAPIErrorFromRaw : IFromRaw { + /// public BetaAPIError FromRawUnchecked(IReadOnlyDictionary rawData) => BetaAPIError.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/BetaAuthenticationError.cs b/src/Anthropic/Models/Beta/BetaAuthenticationError.cs index d62d6693..de8ddca9 100644 --- a/src/Anthropic/Models/Beta/BetaAuthenticationError.cs +++ b/src/Anthropic/Models/Beta/BetaAuthenticationError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaAuthenticationError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public BetaAuthenticationError() this.Type = JsonSerializer.Deserialize("\"authentication_error\""); } + public BetaAuthenticationError(BetaAuthenticationError betaAuthenticationError) + : base(betaAuthenticationError) { } + public BetaAuthenticationError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaAuthenticationError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaAuthenticationError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public BetaAuthenticationError(string message) class BetaAuthenticationErrorFromRaw : IFromRaw { + /// public BetaAuthenticationError FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaAuthenticationError.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/BetaBillingError.cs b/src/Anthropic/Models/Beta/BetaBillingError.cs index 6507768f..c6954f0d 100644 --- a/src/Anthropic/Models/Beta/BetaBillingError.cs +++ b/src/Anthropic/Models/Beta/BetaBillingError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaBillingError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public BetaBillingError() this.Type = JsonSerializer.Deserialize("\"billing_error\""); } + public BetaBillingError(BetaBillingError betaBillingError) + : base(betaBillingError) { } + public BetaBillingError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaBillingError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaBillingError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public BetaBillingError(string message) class BetaBillingErrorFromRaw : IFromRaw { + /// public BetaBillingError FromRawUnchecked(IReadOnlyDictionary rawData) => BetaBillingError.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/BetaError.cs b/src/Anthropic/Models/Beta/BetaError.cs index 23c79353..4f9ebbbf 100644 --- a/src/Anthropic/Models/Beta/BetaError.cs +++ b/src/Anthropic/Models/Beta/BetaError.cs @@ -113,60 +113,222 @@ public BetaError(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickInvalidRequest(out var value)) { + /// // `value` is of type `BetaInvalidRequestError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickInvalidRequest([NotNullWhen(true)] out BetaInvalidRequestError? value) { value = this.Value as BetaInvalidRequestError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickAuthentication(out var value)) { + /// // `value` is of type `BetaAuthenticationError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickAuthentication([NotNullWhen(true)] out BetaAuthenticationError? value) { value = this.Value as BetaAuthenticationError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBilling(out var value)) { + /// // `value` is of type `BetaBillingError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBilling([NotNullWhen(true)] out BetaBillingError? value) { value = this.Value as BetaBillingError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickPermission(out var value)) { + /// // `value` is of type `BetaPermissionError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickPermission([NotNullWhen(true)] out BetaPermissionError? value) { value = this.Value as BetaPermissionError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickNotFound(out var value)) { + /// // `value` is of type `BetaNotFoundError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickNotFound([NotNullWhen(true)] out BetaNotFoundError? value) { value = this.Value as BetaNotFoundError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickRateLimit(out var value)) { + /// // `value` is of type `BetaRateLimitError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickRateLimit([NotNullWhen(true)] out BetaRateLimitError? value) { value = this.Value as BetaRateLimitError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickGatewayTimeout(out var value)) { + /// // `value` is of type `BetaGatewayTimeoutError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickGatewayTimeout([NotNullWhen(true)] out BetaGatewayTimeoutError? value) { value = this.Value as BetaGatewayTimeoutError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickAPI(out var value)) { + /// // `value` is of type `BetaAPIError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickAPI([NotNullWhen(true)] out BetaAPIError? value) { value = this.Value as BetaAPIError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickOverloaded(out var value)) { + /// // `value` is of type `BetaOverloadedError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickOverloaded([NotNullWhen(true)] out BetaOverloadedError? value) { value = this.Value as BetaOverloadedError; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaInvalidRequestError value) => {...}, + /// (BetaAuthenticationError value) => {...}, + /// (BetaBillingError value) => {...}, + /// (BetaPermissionError value) => {...}, + /// (BetaNotFoundError value) => {...}, + /// (BetaRateLimitError value) => {...}, + /// (BetaGatewayTimeoutError value) => {...}, + /// (BetaAPIError value) => {...}, + /// (BetaOverloadedError value) => {...} + /// ); + /// + /// + /// public void Switch( Action invalidRequest, Action authentication, @@ -215,6 +377,34 @@ Action overloaded } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaInvalidRequestError value) => {...}, + /// (BetaAuthenticationError value) => {...}, + /// (BetaBillingError value) => {...}, + /// (BetaPermissionError value) => {...}, + /// (BetaNotFoundError value) => {...}, + /// (BetaRateLimitError value) => {...}, + /// (BetaGatewayTimeoutError value) => {...}, + /// (BetaAPIError value) => {...}, + /// (BetaOverloadedError value) => {...} + /// ); + /// + /// + /// public T Match( Func invalidRequest, Func authentication, @@ -262,12 +452,43 @@ Func overloaded public static implicit operator BetaError(BetaOverloadedError value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of BetaError"); } + this.Switch( + (invalidRequest) => invalidRequest.Validate(), + (authentication) => authentication.Validate(), + (billing) => billing.Validate(), + (permission) => permission.Validate(), + (notFound) => notFound.Validate(), + (rateLimit) => rateLimit.Validate(), + (gatewayTimeout) => gatewayTimeout.Validate(), + (api) => api.Validate(), + (overloaded) => overloaded.Validate() + ); + } + + public virtual bool Equals(BetaError? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/BetaErrorResponse.cs b/src/Anthropic/Models/Beta/BetaErrorResponse.cs index b51ba2ed..7e2b3405 100644 --- a/src/Anthropic/Models/Beta/BetaErrorResponse.cs +++ b/src/Anthropic/Models/Beta/BetaErrorResponse.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,68 +13,23 @@ public sealed record class BetaErrorResponse : ModelBase { public required BetaError Error { - get - { - if (!this._rawData.TryGetValue("error", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error' cannot be null", - new ArgumentOutOfRangeException("error", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'error' cannot be null", - new ArgumentNullException("error") - ); - } - init - { - this._rawData["error"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "error"); } + init { ModelBase.Set(this._rawData, "error", value); } } public required string? RequestID { - get - { - if (!this._rawData.TryGetValue("request_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["request_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "request_id"); } + init { ModelBase.Set(this._rawData, "request_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Error.Validate(); @@ -93,6 +47,9 @@ public BetaErrorResponse() this.Type = JsonSerializer.Deserialize("\"error\""); } + public BetaErrorResponse(BetaErrorResponse betaErrorResponse) + : base(betaErrorResponse) { } + public BetaErrorResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -108,6 +65,7 @@ public BetaErrorResponse(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaErrorResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -118,6 +76,7 @@ IReadOnlyDictionary rawData class BetaErrorResponseFromRaw : IFromRaw { + /// public BetaErrorResponse FromRawUnchecked(IReadOnlyDictionary rawData) => BetaErrorResponse.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/BetaGatewayTimeoutError.cs b/src/Anthropic/Models/Beta/BetaGatewayTimeoutError.cs index 2c445452..c6f04d3f 100644 --- a/src/Anthropic/Models/Beta/BetaGatewayTimeoutError.cs +++ b/src/Anthropic/Models/Beta/BetaGatewayTimeoutError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaGatewayTimeoutError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public BetaGatewayTimeoutError() this.Type = JsonSerializer.Deserialize("\"timeout_error\""); } + public BetaGatewayTimeoutError(BetaGatewayTimeoutError betaGatewayTimeoutError) + : base(betaGatewayTimeoutError) { } + public BetaGatewayTimeoutError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaGatewayTimeoutError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaGatewayTimeoutError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public BetaGatewayTimeoutError(string message) class BetaGatewayTimeoutErrorFromRaw : IFromRaw { + /// public BetaGatewayTimeoutError FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaGatewayTimeoutError.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/BetaInvalidRequestError.cs b/src/Anthropic/Models/Beta/BetaInvalidRequestError.cs index 6b371f15..49a370d2 100644 --- a/src/Anthropic/Models/Beta/BetaInvalidRequestError.cs +++ b/src/Anthropic/Models/Beta/BetaInvalidRequestError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaInvalidRequestError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public BetaInvalidRequestError() this.Type = JsonSerializer.Deserialize("\"invalid_request_error\""); } + public BetaInvalidRequestError(BetaInvalidRequestError betaInvalidRequestError) + : base(betaInvalidRequestError) { } + public BetaInvalidRequestError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaInvalidRequestError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaInvalidRequestError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public BetaInvalidRequestError(string message) class BetaInvalidRequestErrorFromRaw : IFromRaw { + /// public BetaInvalidRequestError FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaInvalidRequestError.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/BetaNotFoundError.cs b/src/Anthropic/Models/Beta/BetaNotFoundError.cs index 46942814..070018e7 100644 --- a/src/Anthropic/Models/Beta/BetaNotFoundError.cs +++ b/src/Anthropic/Models/Beta/BetaNotFoundError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaNotFoundError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public BetaNotFoundError() this.Type = JsonSerializer.Deserialize("\"not_found_error\""); } + public BetaNotFoundError(BetaNotFoundError betaNotFoundError) + : base(betaNotFoundError) { } + public BetaNotFoundError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaNotFoundError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaNotFoundError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public BetaNotFoundError(string message) class BetaNotFoundErrorFromRaw : IFromRaw { + /// public BetaNotFoundError FromRawUnchecked(IReadOnlyDictionary rawData) => BetaNotFoundError.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/BetaOverloadedError.cs b/src/Anthropic/Models/Beta/BetaOverloadedError.cs index f0e2c8da..338a6482 100644 --- a/src/Anthropic/Models/Beta/BetaOverloadedError.cs +++ b/src/Anthropic/Models/Beta/BetaOverloadedError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaOverloadedError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public BetaOverloadedError() this.Type = JsonSerializer.Deserialize("\"overloaded_error\""); } + public BetaOverloadedError(BetaOverloadedError betaOverloadedError) + : base(betaOverloadedError) { } + public BetaOverloadedError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaOverloadedError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaOverloadedError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public BetaOverloadedError(string message) class BetaOverloadedErrorFromRaw : IFromRaw { + /// public BetaOverloadedError FromRawUnchecked(IReadOnlyDictionary rawData) => BetaOverloadedError.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/BetaPermissionError.cs b/src/Anthropic/Models/Beta/BetaPermissionError.cs index 6deb8910..d8d2e39d 100644 --- a/src/Anthropic/Models/Beta/BetaPermissionError.cs +++ b/src/Anthropic/Models/Beta/BetaPermissionError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaPermissionError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public BetaPermissionError() this.Type = JsonSerializer.Deserialize("\"permission_error\""); } + public BetaPermissionError(BetaPermissionError betaPermissionError) + : base(betaPermissionError) { } + public BetaPermissionError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaPermissionError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaPermissionError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public BetaPermissionError(string message) class BetaPermissionErrorFromRaw : IFromRaw { + /// public BetaPermissionError FromRawUnchecked(IReadOnlyDictionary rawData) => BetaPermissionError.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/BetaRateLimitError.cs b/src/Anthropic/Models/Beta/BetaRateLimitError.cs index 82fdcfdb..e0ce4e3c 100644 --- a/src/Anthropic/Models/Beta/BetaRateLimitError.cs +++ b/src/Anthropic/Models/Beta/BetaRateLimitError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaRateLimitError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public BetaRateLimitError() this.Type = JsonSerializer.Deserialize("\"rate_limit_error\""); } + public BetaRateLimitError(BetaRateLimitError betaRateLimitError) + : base(betaRateLimitError) { } + public BetaRateLimitError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaRateLimitError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaRateLimitError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public BetaRateLimitError(string message) class BetaRateLimitErrorFromRaw : IFromRaw { + /// public BetaRateLimitError FromRawUnchecked(IReadOnlyDictionary rawData) => BetaRateLimitError.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Files/DeletedFile.cs b/src/Anthropic/Models/Beta/Files/DeletedFile.cs index b87238c1..2196d9b7 100644 --- a/src/Anthropic/Models/Beta/Files/DeletedFile.cs +++ b/src/Anthropic/Models/Beta/Files/DeletedFile.cs @@ -17,27 +17,8 @@ public sealed record class DeletedFile : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new System::ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new System::ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -49,13 +30,9 @@ public required string ID { get { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); + return ModelBase.GetNullableClass< + ApiEnum + >(this.RawData, "type"); } init { @@ -64,13 +41,11 @@ public required string ID return; } - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ID; @@ -79,6 +54,9 @@ public override void Validate() public DeletedFile() { } + public DeletedFile(DeletedFile deletedFile) + : base(deletedFile) { } + public DeletedFile(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +70,7 @@ public DeletedFile(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static DeletedFile FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -107,6 +86,7 @@ public DeletedFile(string id) class DeletedFileFromRaw : IFromRaw { + /// public DeletedFile FromRawUnchecked(IReadOnlyDictionary rawData) => DeletedFile.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Files/FileDeleteParams.cs b/src/Anthropic/Models/Beta/Files/FileDeleteParams.cs index 415800fb..d9e0e048 100644 --- a/src/Anthropic/Models/Beta/Files/FileDeleteParams.cs +++ b/src/Anthropic/Models/Beta/Files/FileDeleteParams.cs @@ -23,12 +23,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -38,15 +35,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public FileDeleteParams() { } + public FileDeleteParams(FileDeleteParams fileDeleteParams) + : base(fileDeleteParams) { } + public FileDeleteParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -68,6 +65,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static FileDeleteParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Files/FileDownloadParams.cs b/src/Anthropic/Models/Beta/Files/FileDownloadParams.cs index 25dd7098..1cc2327f 100644 --- a/src/Anthropic/Models/Beta/Files/FileDownloadParams.cs +++ b/src/Anthropic/Models/Beta/Files/FileDownloadParams.cs @@ -23,12 +23,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -38,15 +35,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public FileDownloadParams() { } + public FileDownloadParams(FileDownloadParams fileDownloadParams) + : base(fileDownloadParams) { } + public FileDownloadParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -68,6 +65,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static FileDownloadParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Files/FileListPageResponse.cs b/src/Anthropic/Models/Beta/Files/FileListPageResponse.cs index fe0618fd..5e8ca686 100644 --- a/src/Anthropic/Models/Beta/Files/FileListPageResponse.cs +++ b/src/Anthropic/Models/Beta/Files/FileListPageResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Files; @@ -17,30 +15,8 @@ public sealed record class FileListPageResponse : ModelBase /// public required IReadOnlyList Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } /// @@ -48,20 +24,8 @@ public required IReadOnlyList Data /// public string? FirstID { - get - { - if (!this._rawData.TryGetValue("first_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["first_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "first_id"); } + init { ModelBase.Set(this._rawData, "first_id", value); } } /// @@ -69,13 +33,7 @@ public string? FirstID /// public bool? HasMore { - get - { - if (!this._rawData.TryGetValue("has_more", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "has_more"); } init { if (value == null) @@ -83,10 +41,7 @@ public bool? HasMore return; } - this._rawData["has_more"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "has_more", value); } } @@ -95,22 +50,11 @@ public bool? HasMore /// public string? LastID { - get - { - if (!this._rawData.TryGetValue("last_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["last_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "last_id"); } + init { ModelBase.Set(this._rawData, "last_id", value); } } + /// public override void Validate() { foreach (var item in this.Data) @@ -124,6 +68,9 @@ public override void Validate() public FileListPageResponse() { } + public FileListPageResponse(FileListPageResponse fileListPageResponse) + : base(fileListPageResponse) { } + public FileListPageResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -137,6 +84,7 @@ public FileListPageResponse(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static FileListPageResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -154,6 +102,7 @@ public FileListPageResponse(List data) class FileListPageResponseFromRaw : IFromRaw { + /// public FileListPageResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => FileListPageResponse.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Files/FileListParams.cs b/src/Anthropic/Models/Beta/Files/FileListParams.cs index 0f2e07b0..99020dab 100644 --- a/src/Anthropic/Models/Beta/Files/FileListParams.cs +++ b/src/Anthropic/Models/Beta/Files/FileListParams.cs @@ -20,13 +20,7 @@ public sealed record class FileListParams : ParamsBase /// public string? AfterID { - get - { - if (!this._rawQueryData.TryGetValue("after_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawQueryData, "after_id"); } init { if (value == null) @@ -34,10 +28,7 @@ public string? AfterID return; } - this._rawQueryData["after_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "after_id", value); } } @@ -47,13 +38,7 @@ public string? AfterID /// public string? BeforeID { - get - { - if (!this._rawQueryData.TryGetValue("before_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawQueryData, "before_id"); } init { if (value == null) @@ -61,10 +46,7 @@ public string? BeforeID return; } - this._rawQueryData["before_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "before_id", value); } } @@ -75,13 +57,7 @@ public string? BeforeID /// public long? Limit { - get - { - if (!this._rawQueryData.TryGetValue("limit", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawQueryData, "limit"); } init { if (value == null) @@ -89,10 +65,7 @@ public long? Limit return; } - this._rawQueryData["limit"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "limit", value); } } @@ -103,12 +76,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -118,15 +88,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public FileListParams() { } + public FileListParams(FileListParams fileListParams) + : base(fileListParams) { } + public FileListParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -148,6 +118,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static FileListParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Files/FileMetadata.cs b/src/Anthropic/Models/Beta/Files/FileMetadata.cs index f35d66ab..cf56b11d 100644 --- a/src/Anthropic/Models/Beta/Files/FileMetadata.cs +++ b/src/Anthropic/Models/Beta/Files/FileMetadata.cs @@ -19,27 +19,8 @@ public sealed record class FileMetadata : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -47,23 +28,8 @@ public required string ID /// public required DateTimeOffset CreatedAt { - get - { - if (!this._rawData.TryGetValue("created_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new ArgumentOutOfRangeException("created_at", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["created_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "created_at"); } + init { ModelBase.Set(this._rawData, "created_at", value); } } /// @@ -71,27 +37,8 @@ public required DateTimeOffset CreatedAt /// public required string Filename { - get - { - if (!this._rawData.TryGetValue("filename", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'filename' cannot be null", - new ArgumentOutOfRangeException("filename", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'filename' cannot be null", - new ArgumentNullException("filename") - ); - } - init - { - this._rawData["filename"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "filename"); } + init { ModelBase.Set(this._rawData, "filename", value); } } /// @@ -99,27 +46,8 @@ public required string Filename /// public required string MimeType { - get - { - if (!this._rawData.TryGetValue("mime_type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'mime_type' cannot be null", - new ArgumentOutOfRangeException("mime_type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'mime_type' cannot be null", - new ArgumentNullException("mime_type") - ); - } - init - { - this._rawData["mime_type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "mime_type"); } + init { ModelBase.Set(this._rawData, "mime_type", value); } } /// @@ -127,23 +55,8 @@ public required string MimeType /// public required long SizeBytes { - get - { - if (!this._rawData.TryGetValue("size_bytes", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'size_bytes' cannot be null", - new ArgumentOutOfRangeException("size_bytes", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["size_bytes"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "size_bytes"); } + init { ModelBase.Set(this._rawData, "size_bytes", value); } } /// @@ -153,23 +66,8 @@ public required long SizeBytes /// public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -177,13 +75,7 @@ public JsonElement Type /// public bool? Downloadable { - get - { - if (!this._rawData.TryGetValue("downloadable", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "downloadable"); } init { if (value == null) @@ -191,13 +83,11 @@ public bool? Downloadable return; } - this._rawData["downloadable"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "downloadable", value); } } + /// public override void Validate() { _ = this.ID; @@ -217,6 +107,9 @@ public FileMetadata() this.Type = JsonSerializer.Deserialize("\"file\""); } + public FileMetadata(FileMetadata fileMetadata) + : base(fileMetadata) { } + public FileMetadata(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -232,6 +125,7 @@ public FileMetadata(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static FileMetadata FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -240,6 +134,7 @@ public static FileMetadata FromRawUnchecked(IReadOnlyDictionary { + /// public FileMetadata FromRawUnchecked(IReadOnlyDictionary rawData) => FileMetadata.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Files/FileRetrieveMetadataParams.cs b/src/Anthropic/Models/Beta/Files/FileRetrieveMetadataParams.cs index 4a8aca07..e8b44028 100644 --- a/src/Anthropic/Models/Beta/Files/FileRetrieveMetadataParams.cs +++ b/src/Anthropic/Models/Beta/Files/FileRetrieveMetadataParams.cs @@ -23,12 +23,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -38,15 +35,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public FileRetrieveMetadataParams() { } + public FileRetrieveMetadataParams(FileRetrieveMetadataParams fileRetrieveMetadataParams) + : base(fileRetrieveMetadataParams) { } + public FileRetrieveMetadataParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -68,6 +65,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static FileRetrieveMetadataParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BatchCancelParams.cs b/src/Anthropic/Models/Beta/Messages/Batches/BatchCancelParams.cs index 9d97d140..01ec01ba 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BatchCancelParams.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BatchCancelParams.cs @@ -31,12 +31,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -46,15 +43,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public BatchCancelParams() { } + public BatchCancelParams(BatchCancelParams batchCancelParams) + : base(batchCancelParams) { } + public BatchCancelParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -76,6 +73,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static BatchCancelParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BatchCreateParams.cs b/src/Anthropic/Models/Beta/Messages/Batches/BatchCreateParams.cs index 75a81f2a..847e62c4 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BatchCreateParams.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BatchCreateParams.cs @@ -37,27 +37,8 @@ public IReadOnlyDictionary RawBodyData /// public required IReadOnlyList Requests { - get - { - if (!this._rawBodyData.TryGetValue("requests", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'requests' cannot be null", - new System::ArgumentOutOfRangeException("requests", "Missing required argument") - ); - - return JsonSerializer.Deserialize>(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'requests' cannot be null", - new System::ArgumentNullException("requests") - ); - } - init - { - this._rawBodyData["requests"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawBodyData, "requests"); } + init { ModelBase.Set(this._rawBodyData, "requests", value); } } /// @@ -67,12 +48,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -82,15 +60,18 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public BatchCreateParams() { } + public BatchCreateParams(BatchCreateParams batchCreateParams) + : base(batchCreateParams) + { + this._rawBodyData = [.. batchCreateParams._rawBodyData]; + } + public BatchCreateParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, @@ -116,6 +97,7 @@ FrozenDictionary rawBodyData } #pragma warning restore CS8618 + /// public static BatchCreateParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, @@ -166,30 +148,8 @@ public sealed record class Request : ModelBase /// public required string CustomID { - get - { - if (!this._rawData.TryGetValue("custom_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'custom_id' cannot be null", - new System::ArgumentOutOfRangeException( - "custom_id", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'custom_id' cannot be null", - new System::ArgumentNullException("custom_id") - ); - } - init - { - this._rawData["custom_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "custom_id"); } + init { ModelBase.Set(this._rawData, "custom_id", value); } } /// @@ -200,29 +160,11 @@ public required string CustomID /// public required Params Params { - get - { - if (!this._rawData.TryGetValue("params", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'params' cannot be null", - new System::ArgumentOutOfRangeException("params", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'params' cannot be null", - new System::ArgumentNullException("params") - ); - } - init - { - this._rawData["params"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "params"); } + init { ModelBase.Set(this._rawData, "params", value); } } + /// public override void Validate() { _ = this.CustomID; @@ -231,6 +173,9 @@ public override void Validate() public Request() { } + public Request(Request request) + : base(request) { } + public Request(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -244,6 +189,7 @@ public Request(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static Request FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -252,6 +198,7 @@ public static Request FromRawUnchecked(IReadOnlyDictionary class RequestFromRaw : IFromRaw { + /// public Request FromRawUnchecked(IReadOnlyDictionary rawData) => Request.FromRawUnchecked(rawData); } @@ -276,26 +223,8 @@ public sealed record class Params : ModelBase /// public required long MaxTokens { - get - { - if (!this._rawData.TryGetValue("max_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'max_tokens' cannot be null", - new System::ArgumentOutOfRangeException( - "max_tokens", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["max_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "max_tokens"); } + init { ModelBase.Set(this._rawData, "max_tokens", value); } } /// @@ -351,30 +280,8 @@ public required long MaxTokens /// public required IReadOnlyList Messages { - get - { - if (!this._rawData.TryGetValue("messages", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'messages' cannot be null", - new System::ArgumentOutOfRangeException("messages", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'messages' cannot be null", - new System::ArgumentNullException("messages") - ); - } - init - { - this._rawData["messages"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "messages"); } + init { ModelBase.Set(this._rawData, "messages", value); } } /// @@ -383,26 +290,8 @@ public required IReadOnlyList Messages /// public required ApiEnum Model { - get - { - if (!this._rawData.TryGetValue("model", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'model' cannot be null", - new System::ArgumentOutOfRangeException("model", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["model"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "model"); } + init { ModelBase.Set(this._rawData, "model", value); } } /// @@ -412,21 +301,12 @@ public required ApiEnum Model { get { - if (!this._rawData.TryGetValue("container", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["container"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "container" ); } + init { ModelBase.Set(this._rawData, "container", value); } } /// @@ -439,21 +319,12 @@ public BetaContextManagementConfig? ContextManagement { get { - if (!this._rawData.TryGetValue("context_management", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["context_management"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "context_management" ); } + init { ModelBase.Set(this._rawData, "context_management", value); } } /// @@ -463,12 +334,9 @@ public IReadOnlyList? MCPServers { get { - if (!this._rawData.TryGetValue("mcp_servers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawData, + "mcp_servers" ); } init @@ -478,10 +346,7 @@ public IReadOnlyList? MCPServers return; } - this._rawData["mcp_servers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "mcp_servers", value); } } @@ -490,13 +355,7 @@ public IReadOnlyList? MCPServers /// public BetaMetadata? Metadata { - get - { - if (!this._rawData.TryGetValue("metadata", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawData, "metadata"); } init { if (value == null) @@ -504,10 +363,7 @@ public BetaMetadata? Metadata return; } - this._rawData["metadata"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "metadata", value); } } @@ -517,16 +373,7 @@ public BetaMetadata? Metadata /// public BetaOutputConfig? OutputConfig { - get - { - if (!this._rawData.TryGetValue("output_config", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "output_config"); } init { if (value == null) @@ -534,10 +381,7 @@ public BetaOutputConfig? OutputConfig return; } - this._rawData["output_config"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "output_config", value); } } @@ -548,21 +392,9 @@ public BetaJSONOutputFormat? OutputFormat { get { - if (!this._rawData.TryGetValue("output_format", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["output_format"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "output_format"); } + init { ModelBase.Set(this._rawData, "output_format", value); } } /// @@ -576,13 +408,9 @@ public BetaJSONOutputFormat? OutputFormat { get { - if (!this._rawData.TryGetValue("service_tier", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); + return ModelBase.GetNullableClass< + ApiEnum + >(this.RawData, "service_tier"); } init { @@ -591,10 +419,7 @@ public BetaJSONOutputFormat? OutputFormat return; } - this._rawData["service_tier"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "service_tier", value); } } @@ -612,13 +437,7 @@ public BetaJSONOutputFormat? OutputFormat /// public IReadOnlyList? StopSequences { - get - { - if (!this._rawData.TryGetValue("stop_sequences", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass>(this.RawData, "stop_sequences"); } init { if (value == null) @@ -626,10 +445,7 @@ public IReadOnlyList? StopSequences return; } - this._rawData["stop_sequences"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "stop_sequences", value); } } @@ -641,13 +457,7 @@ public IReadOnlyList? StopSequences /// public bool? Stream { - get - { - if (!this._rawData.TryGetValue("stream", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "stream"); } init { if (value == null) @@ -655,10 +465,7 @@ public bool? Stream return; } - this._rawData["stream"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "stream", value); } } @@ -670,13 +477,7 @@ public bool? Stream /// public ParamsSystem? System { - get - { - if (!this._rawData.TryGetValue("system", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawData, "system"); } init { if (value == null) @@ -684,10 +485,7 @@ public ParamsSystem? System return; } - this._rawData["system"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "system", value); } } @@ -703,13 +501,7 @@ public ParamsSystem? System /// public double? Temperature { - get - { - if (!this._rawData.TryGetValue("temperature", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "temperature"); } init { if (value == null) @@ -717,10 +509,7 @@ public double? Temperature return; } - this._rawData["temperature"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "temperature", value); } } @@ -738,13 +527,7 @@ public BetaThinkingConfigParam? Thinking { get { - if (!this._rawData.TryGetValue("thinking", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "thinking"); } init { @@ -753,10 +536,7 @@ public BetaThinkingConfigParam? Thinking return; } - this._rawData["thinking"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "thinking", value); } } @@ -766,16 +546,7 @@ public BetaThinkingConfigParam? Thinking /// public BetaToolChoice? ToolChoice { - get - { - if (!this._rawData.TryGetValue("tool_choice", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "tool_choice"); } init { if (value == null) @@ -783,10 +554,7 @@ public BetaToolChoice? ToolChoice return; } - this._rawData["tool_choice"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "tool_choice", value); } } @@ -839,16 +607,7 @@ public BetaToolChoice? ToolChoice /// public IReadOnlyList? Tools { - get - { - if (!this._rawData.TryGetValue("tools", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "tools"); } init { if (value == null) @@ -856,10 +615,7 @@ public IReadOnlyList? Tools return; } - this._rawData["tools"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "tools", value); } } @@ -873,13 +629,7 @@ public IReadOnlyList? Tools /// public long? TopK { - get - { - if (!this._rawData.TryGetValue("top_k", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "top_k"); } init { if (value == null) @@ -887,10 +637,7 @@ public long? TopK return; } - this._rawData["top_k"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "top_k", value); } } @@ -906,13 +653,7 @@ public long? TopK /// public double? TopP { - get - { - if (!this._rawData.TryGetValue("top_p", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "top_p"); } init { if (value == null) @@ -920,13 +661,11 @@ public double? TopP return; } - this._rawData["top_p"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "top_p", value); } } + /// public override void Validate() { _ = this.MaxTokens; @@ -961,6 +700,9 @@ public override void Validate() public Params() { } + public Params(Params params1) + : base(params1) { } + public Params(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -974,6 +716,7 @@ public Params(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static Params FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -982,6 +725,7 @@ public static Params FromRawUnchecked(IReadOnlyDictionary r class ParamsFromRaw : IFromRaw { + /// public Params FromRawUnchecked(IReadOnlyDictionary rawData) => Params.FromRawUnchecked(rawData); } @@ -1018,18 +762,68 @@ public Container(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaContainerParams(out var value)) { + /// // `value` is of type `BetaContainerParams` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaContainerParams([NotNullWhen(true)] out BetaContainerParams? value) { value = this.Value as BetaContainerParams; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaContainerParams value) => {...}, + /// (string value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaContainerParams, System::Action @string @@ -1050,6 +844,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaContainerParams value) => {...}, + /// (string value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaContainerParams, System::Func @string @@ -1073,12 +888,33 @@ BetaContainerParams value string value ) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of Container"); } + this.Switch((betaContainerParams) => betaContainerParams.Validate(), (_) => { }); + } + + public virtual bool Equals(global::Anthropic.Models.Beta.Messages.Batches.Container? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } @@ -1226,12 +1062,42 @@ public ParamsSystem(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaTextBlockParams(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaTextBlockParams( [NotNullWhen(true)] out IReadOnlyList? value ) @@ -1240,6 +1106,26 @@ public bool TryPickBetaTextBlockParams( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action @string, System::Action> betaTextBlockParams @@ -1260,6 +1146,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match( System::Func @string, System::Func, T> betaTextBlockParams @@ -1280,6 +1187,16 @@ public T Match( public static implicit operator ParamsSystem(List value) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -1289,6 +1206,16 @@ public void Validate() ); } } + + public virtual bool Equals(ParamsSystem? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } } sealed class ParamsSystemConverter : JsonConverter diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BatchDeleteParams.cs b/src/Anthropic/Models/Beta/Messages/Batches/BatchDeleteParams.cs index 46bdb7fe..efa78540 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BatchDeleteParams.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BatchDeleteParams.cs @@ -28,12 +28,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -43,15 +40,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public BatchDeleteParams() { } + public BatchDeleteParams(BatchDeleteParams batchDeleteParams) + : base(batchDeleteParams) { } + public BatchDeleteParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -73,6 +70,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static BatchDeleteParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BatchListPageResponse.cs b/src/Anthropic/Models/Beta/Messages/Batches/BatchListPageResponse.cs index 6bebe943..aadee598 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BatchListPageResponse.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BatchListPageResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Messages.Batches; @@ -14,30 +12,8 @@ public sealed record class BatchListPageResponse : ModelBase { public required IReadOnlyList Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } /// @@ -45,20 +21,8 @@ public required IReadOnlyList Data /// public required string? FirstID { - get - { - if (!this._rawData.TryGetValue("first_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["first_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "first_id"); } + init { ModelBase.Set(this._rawData, "first_id", value); } } /// @@ -66,23 +30,8 @@ public required string? FirstID /// public required bool HasMore { - get - { - if (!this._rawData.TryGetValue("has_more", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'has_more' cannot be null", - new ArgumentOutOfRangeException("has_more", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["has_more"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "has_more"); } + init { ModelBase.Set(this._rawData, "has_more", value); } } /// @@ -90,22 +39,11 @@ public required bool HasMore /// public required string? LastID { - get - { - if (!this._rawData.TryGetValue("last_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["last_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "last_id"); } + init { ModelBase.Set(this._rawData, "last_id", value); } } + /// public override void Validate() { foreach (var item in this.Data) @@ -119,6 +57,9 @@ public override void Validate() public BatchListPageResponse() { } + public BatchListPageResponse(BatchListPageResponse batchListPageResponse) + : base(batchListPageResponse) { } + public BatchListPageResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -132,6 +73,7 @@ public BatchListPageResponse(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BatchListPageResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -142,6 +84,7 @@ IReadOnlyDictionary rawData class BatchListPageResponseFromRaw : IFromRaw { + /// public BatchListPageResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => BatchListPageResponse.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BatchListParams.cs b/src/Anthropic/Models/Beta/Messages/Batches/BatchListParams.cs index 291dfd53..df177785 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BatchListParams.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BatchListParams.cs @@ -23,13 +23,7 @@ public sealed record class BatchListParams : ParamsBase /// public string? AfterID { - get - { - if (!this._rawQueryData.TryGetValue("after_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawQueryData, "after_id"); } init { if (value == null) @@ -37,10 +31,7 @@ public string? AfterID return; } - this._rawQueryData["after_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "after_id", value); } } @@ -50,13 +41,7 @@ public string? AfterID /// public string? BeforeID { - get - { - if (!this._rawQueryData.TryGetValue("before_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawQueryData, "before_id"); } init { if (value == null) @@ -64,10 +49,7 @@ public string? BeforeID return; } - this._rawQueryData["before_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "before_id", value); } } @@ -78,13 +60,7 @@ public string? BeforeID /// public long? Limit { - get - { - if (!this._rawQueryData.TryGetValue("limit", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawQueryData, "limit"); } init { if (value == null) @@ -92,10 +68,7 @@ public long? Limit return; } - this._rawQueryData["limit"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "limit", value); } } @@ -106,12 +79,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -121,15 +91,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public BatchListParams() { } + public BatchListParams(BatchListParams batchListParams) + : base(batchListParams) { } + public BatchListParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -151,6 +121,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static BatchListParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BatchResultsParams.cs b/src/Anthropic/Models/Beta/Messages/Batches/BatchResultsParams.cs index d71d3be7..680bb8ad 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BatchResultsParams.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BatchResultsParams.cs @@ -29,12 +29,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -44,15 +41,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public BatchResultsParams() { } + public BatchResultsParams(BatchResultsParams batchResultsParams) + : base(batchResultsParams) { } + public BatchResultsParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -74,6 +71,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static BatchResultsParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BatchRetrieveParams.cs b/src/Anthropic/Models/Beta/Messages/Batches/BatchRetrieveParams.cs index a985c15f..1501aac5 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BatchRetrieveParams.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BatchRetrieveParams.cs @@ -27,12 +27,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -42,15 +39,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public BatchRetrieveParams() { } + public BatchRetrieveParams(BatchRetrieveParams batchRetrieveParams) + : base(batchRetrieveParams) { } + public BatchRetrieveParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -72,6 +69,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static BatchRetrieveParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BetaDeletedMessageBatch.cs b/src/Anthropic/Models/Beta/Messages/Batches/BetaDeletedMessageBatch.cs index 84e8d867..131fc458 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BetaDeletedMessageBatch.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BetaDeletedMessageBatch.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -17,27 +16,8 @@ public sealed record class BetaDeletedMessageBatch : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -47,25 +27,11 @@ public required string ID /// public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ID; @@ -85,6 +51,9 @@ public BetaDeletedMessageBatch() this.Type = JsonSerializer.Deserialize("\"message_batch_deleted\""); } + public BetaDeletedMessageBatch(BetaDeletedMessageBatch betaDeletedMessageBatch) + : base(betaDeletedMessageBatch) { } + public BetaDeletedMessageBatch(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -100,6 +69,7 @@ public BetaDeletedMessageBatch(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaDeletedMessageBatch FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -117,6 +87,7 @@ public BetaDeletedMessageBatch(string id) class BetaDeletedMessageBatchFromRaw : IFromRaw { + /// public BetaDeletedMessageBatch FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaDeletedMessageBatch.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatch.cs b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatch.cs index 6c42e987..35f76c48 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatch.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatch.cs @@ -19,27 +19,8 @@ public sealed record class BetaMessageBatch : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new System::ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new System::ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -50,21 +31,9 @@ public required string ID { get { - if (!this._rawData.TryGetValue("archived_at", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["archived_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableStruct(this.RawData, "archived_at"); } + init { ModelBase.Set(this._rawData, "archived_at", value); } } /// @@ -75,21 +44,12 @@ public required string ID { get { - if (!this._rawData.TryGetValue("cancel_initiated_at", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cancel_initiated_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableStruct( + this.RawData, + "cancel_initiated_at" ); } + init { ModelBase.Set(this._rawData, "cancel_initiated_at", value); } } /// @@ -100,27 +60,9 @@ public required string ID { get { - if (!this._rawData.TryGetValue("created_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new System::ArgumentOutOfRangeException( - "created_at", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["created_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNotNullStruct(this.RawData, "created_at"); } + init { ModelBase.Set(this._rawData, "created_at", value); } } /// @@ -134,21 +76,9 @@ public required string ID { get { - if (!this._rawData.TryGetValue("ended_at", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["ended_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableStruct(this.RawData, "ended_at"); } + init { ModelBase.Set(this._rawData, "ended_at", value); } } /// @@ -159,27 +89,9 @@ public required string ID { get { - if (!this._rawData.TryGetValue("expires_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'expires_at' cannot be null", - new System::ArgumentOutOfRangeException( - "expires_at", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["expires_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNotNullStruct(this.RawData, "expires_at"); } + init { ModelBase.Set(this._rawData, "expires_at", value); } } /// @@ -189,27 +101,12 @@ public required ApiEnum ProcessingStatus { get { - if (!this._rawData.TryGetValue("processing_status", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'processing_status' cannot be null", - new System::ArgumentOutOfRangeException( - "processing_status", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["processing_status"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "processing_status" ); } + init { ModelBase.Set(this._rawData, "processing_status", value); } } /// @@ -223,31 +120,12 @@ public required BetaMessageBatchRequestCounts RequestCounts { get { - if (!this._rawData.TryGetValue("request_counts", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'request_counts' cannot be null", - new System::ArgumentOutOfRangeException( - "request_counts", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'request_counts' cannot be null", - new System::ArgumentNullException("request_counts") - ); - } - init - { - this._rawData["request_counts"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "request_counts" ); } + init { ModelBase.Set(this._rawData, "request_counts", value); } } /// @@ -259,20 +137,8 @@ public required BetaMessageBatchRequestCounts RequestCounts /// public required string? ResultsURL { - get - { - if (!this._rawData.TryGetValue("results_url", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["results_url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "results_url"); } + init { ModelBase.Set(this._rawData, "results_url", value); } } /// @@ -282,25 +148,11 @@ public required string? ResultsURL /// public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ID; @@ -328,6 +180,9 @@ public BetaMessageBatch() this.Type = JsonSerializer.Deserialize("\"message_batch\""); } + public BetaMessageBatch(BetaMessageBatch betaMessageBatch) + : base(betaMessageBatch) { } + public BetaMessageBatch(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -343,6 +198,7 @@ public BetaMessageBatch(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaMessageBatch FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -353,6 +209,7 @@ IReadOnlyDictionary rawData class BetaMessageBatchFromRaw : IFromRaw { + /// public BetaMessageBatch FromRawUnchecked(IReadOnlyDictionary rawData) => BetaMessageBatch.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchCanceledResult.cs b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchCanceledResult.cs index 33db3561..b039c8c9 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchCanceledResult.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchCanceledResult.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,25 +15,11 @@ public sealed record class BetaMessageBatchCanceledResult : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { if ( @@ -53,6 +38,11 @@ public BetaMessageBatchCanceledResult() this.Type = JsonSerializer.Deserialize("\"canceled\""); } + public BetaMessageBatchCanceledResult( + BetaMessageBatchCanceledResult betaMessageBatchCanceledResult + ) + : base(betaMessageBatchCanceledResult) { } + public BetaMessageBatchCanceledResult(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -68,6 +58,7 @@ public BetaMessageBatchCanceledResult(IReadOnlyDictionary r } #pragma warning restore CS8618 + /// public static BetaMessageBatchCanceledResult FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -78,6 +69,7 @@ IReadOnlyDictionary rawData class BetaMessageBatchCanceledResultFromRaw : IFromRaw { + /// public BetaMessageBatchCanceledResult FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMessageBatchCanceledResult.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchErroredResult.cs b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchErroredResult.cs index 345629dc..13f61698 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchErroredResult.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchErroredResult.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,53 +15,17 @@ public sealed record class BetaMessageBatchErroredResult : ModelBase { public required BetaErrorResponse Error { - get - { - if (!this._rawData.TryGetValue("error", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error' cannot be null", - new ArgumentOutOfRangeException("error", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'error' cannot be null", - new ArgumentNullException("error") - ); - } - init - { - this._rawData["error"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "error"); } + init { ModelBase.Set(this._rawData, "error", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Error.Validate(); @@ -82,6 +45,11 @@ public BetaMessageBatchErroredResult() this.Type = JsonSerializer.Deserialize("\"errored\""); } + public BetaMessageBatchErroredResult( + BetaMessageBatchErroredResult betaMessageBatchErroredResult + ) + : base(betaMessageBatchErroredResult) { } + public BetaMessageBatchErroredResult(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -97,6 +65,7 @@ public BetaMessageBatchErroredResult(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaMessageBatchErroredResult FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -114,6 +83,7 @@ public BetaMessageBatchErroredResult(BetaErrorResponse error) class BetaMessageBatchErroredResultFromRaw : IFromRaw { + /// public BetaMessageBatchErroredResult FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMessageBatchErroredResult.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchExpiredResult.cs b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchExpiredResult.cs index 54376781..59bfd88c 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchExpiredResult.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchExpiredResult.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,25 +15,11 @@ public sealed record class BetaMessageBatchExpiredResult : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { if ( @@ -53,6 +38,11 @@ public BetaMessageBatchExpiredResult() this.Type = JsonSerializer.Deserialize("\"expired\""); } + public BetaMessageBatchExpiredResult( + BetaMessageBatchExpiredResult betaMessageBatchExpiredResult + ) + : base(betaMessageBatchExpiredResult) { } + public BetaMessageBatchExpiredResult(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -68,6 +58,7 @@ public BetaMessageBatchExpiredResult(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaMessageBatchExpiredResult FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -78,6 +69,7 @@ IReadOnlyDictionary rawData class BetaMessageBatchExpiredResultFromRaw : IFromRaw { + /// public BetaMessageBatchExpiredResult FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMessageBatchExpiredResult.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchIndividualResponse.cs b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchIndividualResponse.cs index 89f408c3..0c1c511c 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchIndividualResponse.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchIndividualResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Messages.Batches; @@ -29,27 +27,8 @@ public sealed record class BetaMessageBatchIndividualResponse : ModelBase /// public required string CustomID { - get - { - if (!this._rawData.TryGetValue("custom_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'custom_id' cannot be null", - new ArgumentOutOfRangeException("custom_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'custom_id' cannot be null", - new ArgumentNullException("custom_id") - ); - } - init - { - this._rawData["custom_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "custom_id"); } + init { ModelBase.Set(this._rawData, "custom_id", value); } } /// @@ -61,32 +40,11 @@ public required string CustomID /// public required BetaMessageBatchResult Result { - get - { - if (!this._rawData.TryGetValue("result", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'result' cannot be null", - new ArgumentOutOfRangeException("result", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'result' cannot be null", - new ArgumentNullException("result") - ); - } - init - { - this._rawData["result"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "result"); } + init { ModelBase.Set(this._rawData, "result", value); } } + /// public override void Validate() { _ = this.CustomID; @@ -95,6 +53,11 @@ public override void Validate() public BetaMessageBatchIndividualResponse() { } + public BetaMessageBatchIndividualResponse( + BetaMessageBatchIndividualResponse betaMessageBatchIndividualResponse + ) + : base(betaMessageBatchIndividualResponse) { } + public BetaMessageBatchIndividualResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -108,6 +71,7 @@ public BetaMessageBatchIndividualResponse(IReadOnlyDictionary public static BetaMessageBatchIndividualResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -118,6 +82,7 @@ IReadOnlyDictionary rawData class BetaMessageBatchIndividualResponseFromRaw : IFromRaw { + /// public BetaMessageBatchIndividualResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMessageBatchIndividualResponse.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchRequestCounts.cs b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchRequestCounts.cs index d3fdf989..676775fc 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchRequestCounts.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchRequestCounts.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Messages.Batches; @@ -21,23 +19,8 @@ public sealed record class BetaMessageBatchRequestCounts : ModelBase /// public required long Canceled { - get - { - if (!this._rawData.TryGetValue("canceled", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'canceled' cannot be null", - new ArgumentOutOfRangeException("canceled", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["canceled"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "canceled"); } + init { ModelBase.Set(this._rawData, "canceled", value); } } /// @@ -47,23 +30,8 @@ public required long Canceled /// public required long Errored { - get - { - if (!this._rawData.TryGetValue("errored", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'errored' cannot be null", - new ArgumentOutOfRangeException("errored", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["errored"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "errored"); } + init { ModelBase.Set(this._rawData, "errored", value); } } /// @@ -73,23 +41,8 @@ public required long Errored /// public required long Expired { - get - { - if (!this._rawData.TryGetValue("expired", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'expired' cannot be null", - new ArgumentOutOfRangeException("expired", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["expired"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "expired"); } + init { ModelBase.Set(this._rawData, "expired", value); } } /// @@ -97,23 +50,8 @@ public required long Expired /// public required long Processing { - get - { - if (!this._rawData.TryGetValue("processing", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'processing' cannot be null", - new ArgumentOutOfRangeException("processing", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["processing"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "processing"); } + init { ModelBase.Set(this._rawData, "processing", value); } } /// @@ -123,25 +61,11 @@ public required long Processing /// public required long Succeeded { - get - { - if (!this._rawData.TryGetValue("succeeded", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'succeeded' cannot be null", - new ArgumentOutOfRangeException("succeeded", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["succeeded"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "succeeded"); } + init { ModelBase.Set(this._rawData, "succeeded", value); } } + /// public override void Validate() { _ = this.Canceled; @@ -153,6 +77,11 @@ public override void Validate() public BetaMessageBatchRequestCounts() { } + public BetaMessageBatchRequestCounts( + BetaMessageBatchRequestCounts betaMessageBatchRequestCounts + ) + : base(betaMessageBatchRequestCounts) { } + public BetaMessageBatchRequestCounts(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -166,6 +95,7 @@ public BetaMessageBatchRequestCounts(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaMessageBatchRequestCounts FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -176,6 +106,7 @@ IReadOnlyDictionary rawData class BetaMessageBatchRequestCountsFromRaw : IFromRaw { + /// public BetaMessageBatchRequestCounts FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMessageBatchRequestCounts.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchResult.cs b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchResult.cs index 33f6f5c8..12c4bc0b 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchResult.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchResult.cs @@ -67,30 +67,112 @@ public BetaMessageBatchResult(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickSucceeded(out var value)) { + /// // `value` is of type `BetaMessageBatchSucceededResult` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickSucceeded([NotNullWhen(true)] out BetaMessageBatchSucceededResult? value) { value = this.Value as BetaMessageBatchSucceededResult; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickErrored(out var value)) { + /// // `value` is of type `BetaMessageBatchErroredResult` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickErrored([NotNullWhen(true)] out BetaMessageBatchErroredResult? value) { value = this.Value as BetaMessageBatchErroredResult; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCanceled(out var value)) { + /// // `value` is of type `BetaMessageBatchCanceledResult` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCanceled([NotNullWhen(true)] out BetaMessageBatchCanceledResult? value) { value = this.Value as BetaMessageBatchCanceledResult; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickExpired(out var value)) { + /// // `value` is of type `BetaMessageBatchExpiredResult` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickExpired([NotNullWhen(true)] out BetaMessageBatchExpiredResult? value) { value = this.Value as BetaMessageBatchExpiredResult; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaMessageBatchSucceededResult value) => {...}, + /// (BetaMessageBatchErroredResult value) => {...}, + /// (BetaMessageBatchCanceledResult value) => {...}, + /// (BetaMessageBatchExpiredResult value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action succeeded, System::Action errored, @@ -119,6 +201,29 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaMessageBatchSucceededResult value) => {...}, + /// (BetaMessageBatchErroredResult value) => {...}, + /// (BetaMessageBatchCanceledResult value) => {...}, + /// (BetaMessageBatchExpiredResult value) => {...} + /// ); + /// + /// + /// public T Match( System::Func succeeded, System::Func errored, @@ -150,6 +255,16 @@ public static implicit operator BetaMessageBatchResult(BetaMessageBatchCanceledR public static implicit operator BetaMessageBatchResult(BetaMessageBatchExpiredResult value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -158,6 +273,22 @@ public void Validate() "Data did not match any variant of BetaMessageBatchResult" ); } + this.Switch( + (succeeded) => succeeded.Validate(), + (errored) => errored.Validate(), + (canceled) => canceled.Validate(), + (expired) => expired.Validate() + ); + } + + public virtual bool Equals(BetaMessageBatchResult? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchSucceededResult.cs b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchSucceededResult.cs index 63731653..e0809947 100644 --- a/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchSucceededResult.cs +++ b/src/Anthropic/Models/Beta/Messages/Batches/BetaMessageBatchSucceededResult.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,50 +15,17 @@ public sealed record class BetaMessageBatchSucceededResult : ModelBase { public required BetaMessage Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Message.Validate(); @@ -79,6 +45,11 @@ public BetaMessageBatchSucceededResult() this.Type = JsonSerializer.Deserialize("\"succeeded\""); } + public BetaMessageBatchSucceededResult( + BetaMessageBatchSucceededResult betaMessageBatchSucceededResult + ) + : base(betaMessageBatchSucceededResult) { } + public BetaMessageBatchSucceededResult(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -94,6 +65,7 @@ public BetaMessageBatchSucceededResult(IReadOnlyDictionary } #pragma warning restore CS8618 + /// public static BetaMessageBatchSucceededResult FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -111,6 +83,7 @@ public BetaMessageBatchSucceededResult(BetaMessage message) class BetaMessageBatchSucceededResultFromRaw : IFromRaw { + /// public BetaMessageBatchSucceededResult FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMessageBatchSucceededResult.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaAllThinkingTurns.cs b/src/Anthropic/Models/Beta/Messages/BetaAllThinkingTurns.cs index 7b63fddf..eac2439d 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaAllThinkingTurns.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaAllThinkingTurns.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,25 +13,11 @@ public sealed record class BetaAllThinkingTurns : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { if (!JsonElement.DeepEquals(this.Type, JsonSerializer.Deserialize("\"all\""))) @@ -46,6 +31,9 @@ public BetaAllThinkingTurns() this.Type = JsonSerializer.Deserialize("\"all\""); } + public BetaAllThinkingTurns(BetaAllThinkingTurns betaAllThinkingTurns) + : base(betaAllThinkingTurns) { } + public BetaAllThinkingTurns(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -61,6 +49,7 @@ public BetaAllThinkingTurns(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaAllThinkingTurns FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -71,6 +60,7 @@ IReadOnlyDictionary rawData class BetaAllThinkingTurnsFromRaw : IFromRaw { + /// public BetaAllThinkingTurns FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaAllThinkingTurns.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaBase64ImageSource.cs b/src/Anthropic/Models/Beta/Messages/BetaBase64ImageSource.cs index 39763ffc..bcde9077 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaBase64ImageSource.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaBase64ImageSource.cs @@ -14,77 +14,29 @@ public sealed record class BetaBase64ImageSource : ModelBase { public required string Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new System::ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new System::ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } public required ApiEnum MediaType { get { - if (!this._rawData.TryGetValue("media_type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'media_type' cannot be null", - new System::ArgumentOutOfRangeException( - "media_type", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["media_type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "media_type" ); } + init { ModelBase.Set(this._rawData, "media_type", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Data; @@ -105,6 +57,9 @@ public BetaBase64ImageSource() this.Type = JsonSerializer.Deserialize("\"base64\""); } + public BetaBase64ImageSource(BetaBase64ImageSource betaBase64ImageSource) + : base(betaBase64ImageSource) { } + public BetaBase64ImageSource(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -120,6 +75,7 @@ public BetaBase64ImageSource(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaBase64ImageSource FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -130,6 +86,7 @@ IReadOnlyDictionary rawData class BetaBase64ImageSourceFromRaw : IFromRaw { + /// public BetaBase64ImageSource FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaBase64ImageSource.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaBase64PDFSource.cs b/src/Anthropic/Models/Beta/Messages/BetaBase64PDFSource.cs index 296fdafa..1b7d5e79 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaBase64PDFSource.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaBase64PDFSource.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,71 +13,23 @@ public sealed record class BetaBase64PDFSource : ModelBase { public required string Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } public JsonElement MediaType { - get - { - if (!this._rawData.TryGetValue("media_type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'media_type' cannot be null", - new ArgumentOutOfRangeException("media_type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["media_type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "media_type"); } + init { ModelBase.Set(this._rawData, "media_type", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Data; @@ -108,6 +59,9 @@ public BetaBase64PDFSource() this.Type = JsonSerializer.Deserialize("\"base64\""); } + public BetaBase64PDFSource(BetaBase64PDFSource betaBase64PDFSource) + : base(betaBase64PDFSource) { } + public BetaBase64PDFSource(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -124,6 +78,7 @@ public BetaBase64PDFSource(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaBase64PDFSource FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -141,6 +96,7 @@ public BetaBase64PDFSource(string data) class BetaBase64PDFSourceFromRaw : IFromRaw { + /// public BetaBase64PDFSource FromRawUnchecked(IReadOnlyDictionary rawData) => BetaBase64PDFSource.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionOutputBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionOutputBlock.cs index 0336cfe2..54f2165a 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionOutputBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionOutputBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,50 +18,17 @@ public sealed record class BetaBashCodeExecutionOutputBlock : ModelBase { public required string FileID { - get - { - if (!this._rawData.TryGetValue("file_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentOutOfRangeException("file_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentNullException("file_id") - ); - } - init - { - this._rawData["file_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "file_id"); } + init { ModelBase.Set(this._rawData, "file_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.FileID; @@ -82,6 +48,11 @@ public BetaBashCodeExecutionOutputBlock() this.Type = JsonSerializer.Deserialize("\"bash_code_execution_output\""); } + public BetaBashCodeExecutionOutputBlock( + BetaBashCodeExecutionOutputBlock betaBashCodeExecutionOutputBlock + ) + : base(betaBashCodeExecutionOutputBlock) { } + public BetaBashCodeExecutionOutputBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -97,6 +68,7 @@ public BetaBashCodeExecutionOutputBlock(IReadOnlyDictionary } #pragma warning restore CS8618 + /// public static BetaBashCodeExecutionOutputBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -114,6 +86,7 @@ public BetaBashCodeExecutionOutputBlock(string fileID) class BetaBashCodeExecutionOutputBlockFromRaw : IFromRaw { + /// public BetaBashCodeExecutionOutputBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaBashCodeExecutionOutputBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionOutputBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionOutputBlockParam.cs index 9204a6ad..862ede02 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionOutputBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionOutputBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,50 +18,17 @@ public sealed record class BetaBashCodeExecutionOutputBlockParam : ModelBase { public required string FileID { - get - { - if (!this._rawData.TryGetValue("file_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentOutOfRangeException("file_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentNullException("file_id") - ); - } - init - { - this._rawData["file_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "file_id"); } + init { ModelBase.Set(this._rawData, "file_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.FileID; @@ -82,6 +48,11 @@ public BetaBashCodeExecutionOutputBlockParam() this.Type = JsonSerializer.Deserialize("\"bash_code_execution_output\""); } + public BetaBashCodeExecutionOutputBlockParam( + BetaBashCodeExecutionOutputBlockParam betaBashCodeExecutionOutputBlockParam + ) + : base(betaBashCodeExecutionOutputBlockParam) { } + public BetaBashCodeExecutionOutputBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -97,6 +68,7 @@ public BetaBashCodeExecutionOutputBlockParam(IReadOnlyDictionary public static BetaBashCodeExecutionOutputBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -114,6 +86,7 @@ public BetaBashCodeExecutionOutputBlockParam(string fileID) class BetaBashCodeExecutionOutputBlockParamFromRaw : IFromRaw { + /// public BetaBashCodeExecutionOutputBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaBashCodeExecutionOutputBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionResultBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionResultBlock.cs index 2ce2c6f1..9a7c476e 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionResultBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionResultBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -21,122 +20,39 @@ public required IReadOnlyList Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required long ReturnCode { - get - { - if (!this._rawData.TryGetValue("return_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'return_code' cannot be null", - new ArgumentOutOfRangeException("return_code", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["return_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "return_code"); } + init { ModelBase.Set(this._rawData, "return_code", value); } } public required string Stderr { - get - { - if (!this._rawData.TryGetValue("stderr", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'stderr' cannot be null", - new ArgumentOutOfRangeException("stderr", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'stderr' cannot be null", - new ArgumentNullException("stderr") - ); - } - init - { - this._rawData["stderr"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "stderr"); } + init { ModelBase.Set(this._rawData, "stderr", value); } } public required string Stdout { - get - { - if (!this._rawData.TryGetValue("stdout", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'stdout' cannot be null", - new ArgumentOutOfRangeException("stdout", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'stdout' cannot be null", - new ArgumentNullException("stdout") - ); - } - init - { - this._rawData["stdout"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "stdout"); } + init { ModelBase.Set(this._rawData, "stdout", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { foreach (var item in this.Content) @@ -162,6 +78,11 @@ public BetaBashCodeExecutionResultBlock() this.Type = JsonSerializer.Deserialize("\"bash_code_execution_result\""); } + public BetaBashCodeExecutionResultBlock( + BetaBashCodeExecutionResultBlock betaBashCodeExecutionResultBlock + ) + : base(betaBashCodeExecutionResultBlock) { } + public BetaBashCodeExecutionResultBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -177,6 +98,7 @@ public BetaBashCodeExecutionResultBlock(IReadOnlyDictionary } #pragma warning restore CS8618 + /// public static BetaBashCodeExecutionResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -187,6 +109,7 @@ IReadOnlyDictionary rawData class BetaBashCodeExecutionResultBlockFromRaw : IFromRaw { + /// public BetaBashCodeExecutionResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaBashCodeExecutionResultBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionResultBlockParam.cs index 79351766..c11829f6 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionResultBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -21,122 +20,39 @@ public required IReadOnlyList Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required long ReturnCode { - get - { - if (!this._rawData.TryGetValue("return_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'return_code' cannot be null", - new ArgumentOutOfRangeException("return_code", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["return_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "return_code"); } + init { ModelBase.Set(this._rawData, "return_code", value); } } public required string Stderr { - get - { - if (!this._rawData.TryGetValue("stderr", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'stderr' cannot be null", - new ArgumentOutOfRangeException("stderr", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'stderr' cannot be null", - new ArgumentNullException("stderr") - ); - } - init - { - this._rawData["stderr"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "stderr"); } + init { ModelBase.Set(this._rawData, "stderr", value); } } public required string Stdout { - get - { - if (!this._rawData.TryGetValue("stdout", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'stdout' cannot be null", - new ArgumentOutOfRangeException("stdout", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'stdout' cannot be null", - new ArgumentNullException("stdout") - ); - } - init - { - this._rawData["stdout"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "stdout"); } + init { ModelBase.Set(this._rawData, "stdout", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { foreach (var item in this.Content) @@ -162,6 +78,11 @@ public BetaBashCodeExecutionResultBlockParam() this.Type = JsonSerializer.Deserialize("\"bash_code_execution_result\""); } + public BetaBashCodeExecutionResultBlockParam( + BetaBashCodeExecutionResultBlockParam betaBashCodeExecutionResultBlockParam + ) + : base(betaBashCodeExecutionResultBlockParam) { } + public BetaBashCodeExecutionResultBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -177,6 +98,7 @@ public BetaBashCodeExecutionResultBlockParam(IReadOnlyDictionary public static BetaBashCodeExecutionResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -187,6 +109,7 @@ IReadOnlyDictionary rawData class BetaBashCodeExecutionResultBlockParamFromRaw : IFromRaw { + /// public BetaBashCodeExecutionResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaBashCodeExecutionResultBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultBlock.cs index 94f6a0cc..d0fde1ce 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultBlock.cs @@ -19,78 +19,23 @@ public sealed record class BetaBashCodeExecutionToolResultBlock : ModelBase { public required Content Content { - get - { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "content"); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentOutOfRangeException( - "tool_use_id", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -111,6 +56,11 @@ public BetaBashCodeExecutionToolResultBlock() this.Type = JsonSerializer.Deserialize("\"bash_code_execution_tool_result\""); } + public BetaBashCodeExecutionToolResultBlock( + BetaBashCodeExecutionToolResultBlock betaBashCodeExecutionToolResultBlock + ) + : base(betaBashCodeExecutionToolResultBlock) { } + public BetaBashCodeExecutionToolResultBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -126,6 +76,7 @@ public BetaBashCodeExecutionToolResultBlock(IReadOnlyDictionary public static BetaBashCodeExecutionToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -136,6 +87,7 @@ IReadOnlyDictionary rawData class BetaBashCodeExecutionToolResultBlockFromRaw : IFromRaw { + /// public BetaBashCodeExecutionToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaBashCodeExecutionToolResultBlock.FromRawUnchecked(rawData); @@ -181,6 +133,21 @@ public Content(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaBashCodeExecutionToolResultError(out var value)) { + /// // `value` is of type `BetaBashCodeExecutionToolResultError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaBashCodeExecutionToolResultError( [NotNullWhen(true)] out BetaBashCodeExecutionToolResultError? value ) @@ -189,6 +156,21 @@ public bool TryPickBetaBashCodeExecutionToolResultError( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaBashCodeExecutionResultBlock(out var value)) { + /// // `value` is of type `BetaBashCodeExecutionResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaBashCodeExecutionResultBlock( [NotNullWhen(true)] out BetaBashCodeExecutionResultBlock? value ) @@ -197,6 +179,26 @@ public bool TryPickBetaBashCodeExecutionResultBlock( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaBashCodeExecutionToolResultError value) => {...}, + /// (BetaBashCodeExecutionResultBlock value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaBashCodeExecutionToolResultError, System::Action betaBashCodeExecutionResultBlock @@ -217,6 +219,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaBashCodeExecutionToolResultError value) => {...}, + /// (BetaBashCodeExecutionResultBlock value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaBashCodeExecutionToolResultError, System::Func betaBashCodeExecutionResultBlock @@ -239,12 +262,37 @@ public static implicit operator Content(BetaBashCodeExecutionToolResultError val public static implicit operator Content(BetaBashCodeExecutionResultBlock value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of Content"); } + this.Switch( + (betaBashCodeExecutionToolResultError) => + betaBashCodeExecutionToolResultError.Validate(), + (betaBashCodeExecutionResultBlock) => betaBashCodeExecutionResultBlock.Validate() + ); + } + + public virtual bool Equals(Content? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultBlockParam.cs index cda5b1c6..db818601 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultBlockParam.cs @@ -21,77 +21,24 @@ public required BetaBashCodeExecutionToolResultBlockParamContent Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentOutOfRangeException( - "tool_use_id", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -101,23 +48,15 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -139,6 +78,11 @@ public BetaBashCodeExecutionToolResultBlockParam() this.Type = JsonSerializer.Deserialize("\"bash_code_execution_tool_result\""); } + public BetaBashCodeExecutionToolResultBlockParam( + BetaBashCodeExecutionToolResultBlockParam betaBashCodeExecutionToolResultBlockParam + ) + : base(betaBashCodeExecutionToolResultBlockParam) { } + public BetaBashCodeExecutionToolResultBlockParam( IReadOnlyDictionary rawData ) @@ -156,6 +100,7 @@ IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaBashCodeExecutionToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -167,6 +112,7 @@ IReadOnlyDictionary rawData class BetaBashCodeExecutionToolResultBlockParamFromRaw : IFromRaw { + /// public BetaBashCodeExecutionToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaBashCodeExecutionToolResultBlockParam.FromRawUnchecked(rawData); @@ -218,6 +164,21 @@ public BetaBashCodeExecutionToolResultBlockParamContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaBashCodeExecutionToolResultErrorParam(out var value)) { + /// // `value` is of type `BetaBashCodeExecutionToolResultErrorParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaBashCodeExecutionToolResultErrorParam( [NotNullWhen(true)] out BetaBashCodeExecutionToolResultErrorParam? value ) @@ -226,6 +187,21 @@ public bool TryPickBetaBashCodeExecutionToolResultErrorParam( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaBashCodeExecutionResultBlockParam(out var value)) { + /// // `value` is of type `BetaBashCodeExecutionResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaBashCodeExecutionResultBlockParam( [NotNullWhen(true)] out BetaBashCodeExecutionResultBlockParam? value ) @@ -234,6 +210,26 @@ public bool TryPickBetaBashCodeExecutionResultBlockParam( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaBashCodeExecutionToolResultErrorParam value) => {...}, + /// (BetaBashCodeExecutionResultBlockParam value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaBashCodeExecutionToolResultErrorParam, System::Action betaBashCodeExecutionResultBlockParam @@ -254,6 +250,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaBashCodeExecutionToolResultErrorParam value) => {...}, + /// (BetaBashCodeExecutionResultBlockParam value) => {...} + /// ); + /// + /// + /// public T Match( System::Func< BetaBashCodeExecutionToolResultErrorParam, @@ -283,6 +300,16 @@ public static implicit operator BetaBashCodeExecutionToolResultBlockParamContent BetaBashCodeExecutionResultBlockParam value ) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -291,6 +318,22 @@ public void Validate() "Data did not match any variant of BetaBashCodeExecutionToolResultBlockParamContent" ); } + this.Switch( + (betaBashCodeExecutionToolResultErrorParam) => + betaBashCodeExecutionToolResultErrorParam.Validate(), + (betaBashCodeExecutionResultBlockParam) => + betaBashCodeExecutionResultBlockParam.Validate() + ); + } + + public virtual bool Equals(BetaBashCodeExecutionToolResultBlockParamContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultError.cs b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultError.cs index 04d1407b..6a7dd1ed 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultError.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultError.cs @@ -21,50 +21,21 @@ public required ApiEnum ErrorCode { get { - if (!this._rawData.TryGetValue("error_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error_code' cannot be null", - new System::ArgumentOutOfRangeException( - "error_code", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["error_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "error_code" ); } + init { ModelBase.Set(this._rawData, "error_code", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.ErrorCode.Validate(); @@ -86,6 +57,11 @@ public BetaBashCodeExecutionToolResultError() ); } + public BetaBashCodeExecutionToolResultError( + BetaBashCodeExecutionToolResultError betaBashCodeExecutionToolResultError + ) + : base(betaBashCodeExecutionToolResultError) { } + public BetaBashCodeExecutionToolResultError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -103,6 +79,7 @@ public BetaBashCodeExecutionToolResultError(IReadOnlyDictionary public static BetaBashCodeExecutionToolResultError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -120,6 +97,7 @@ public BetaBashCodeExecutionToolResultError(ApiEnum errorCode class BetaBashCodeExecutionToolResultErrorFromRaw : IFromRaw { + /// public BetaBashCodeExecutionToolResultError FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaBashCodeExecutionToolResultError.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultErrorParam.cs b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultErrorParam.cs index 6e518270..3f0d2505 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultErrorParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaBashCodeExecutionToolResultErrorParam.cs @@ -21,49 +21,20 @@ public required ApiEnum - >(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["error_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + >(this.RawData, "error_code"); } + init { ModelBase.Set(this._rawData, "error_code", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.ErrorCode.Validate(); @@ -85,6 +56,11 @@ public BetaBashCodeExecutionToolResultErrorParam() ); } + public BetaBashCodeExecutionToolResultErrorParam( + BetaBashCodeExecutionToolResultErrorParam betaBashCodeExecutionToolResultErrorParam + ) + : base(betaBashCodeExecutionToolResultErrorParam) { } + public BetaBashCodeExecutionToolResultErrorParam( IReadOnlyDictionary rawData ) @@ -104,6 +80,7 @@ IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaBashCodeExecutionToolResultErrorParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -124,6 +101,7 @@ ApiEnum errorCode class BetaBashCodeExecutionToolResultErrorParamFromRaw : IFromRaw { + /// public BetaBashCodeExecutionToolResultErrorParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaBashCodeExecutionToolResultErrorParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCacheControlEphemeral.cs b/src/Anthropic/Models/Beta/Messages/BetaCacheControlEphemeral.cs index 3a8a033d..d1cfd3b2 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCacheControlEphemeral.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCacheControlEphemeral.cs @@ -14,23 +14,8 @@ public sealed record class BetaCacheControlEphemeral : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -42,16 +27,7 @@ public JsonElement Type /// public ApiEnum? TTL { - get - { - if (!this._rawData.TryGetValue("ttl", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "ttl"); } init { if (value == null) @@ -59,13 +35,11 @@ public ApiEnum? TTL return; } - this._rawData["ttl"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "ttl", value); } } + /// public override void Validate() { if ( @@ -85,6 +59,9 @@ public BetaCacheControlEphemeral() this.Type = JsonSerializer.Deserialize("\"ephemeral\""); } + public BetaCacheControlEphemeral(BetaCacheControlEphemeral betaCacheControlEphemeral) + : base(betaCacheControlEphemeral) { } + public BetaCacheControlEphemeral(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -100,6 +77,7 @@ public BetaCacheControlEphemeral(IReadOnlyDictionary rawDat } #pragma warning restore CS8618 + /// public static BetaCacheControlEphemeral FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -110,6 +88,7 @@ IReadOnlyDictionary rawData class BetaCacheControlEphemeralFromRaw : IFromRaw { + /// public BetaCacheControlEphemeral FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCacheControlEphemeral.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCacheCreation.cs b/src/Anthropic/Models/Beta/Messages/BetaCacheCreation.cs index 0ecb9a88..a16f2700 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCacheCreation.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCacheCreation.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Messages; @@ -17,26 +15,8 @@ public sealed record class BetaCacheCreation : ModelBase /// public required long Ephemeral1hInputTokens { - get - { - if (!this._rawData.TryGetValue("ephemeral_1h_input_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'ephemeral_1h_input_tokens' cannot be null", - new ArgumentOutOfRangeException( - "ephemeral_1h_input_tokens", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["ephemeral_1h_input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "ephemeral_1h_input_tokens"); } + init { ModelBase.Set(this._rawData, "ephemeral_1h_input_tokens", value); } } /// @@ -44,28 +24,11 @@ public required long Ephemeral1hInputTokens /// public required long Ephemeral5mInputTokens { - get - { - if (!this._rawData.TryGetValue("ephemeral_5m_input_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'ephemeral_5m_input_tokens' cannot be null", - new ArgumentOutOfRangeException( - "ephemeral_5m_input_tokens", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["ephemeral_5m_input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "ephemeral_5m_input_tokens"); } + init { ModelBase.Set(this._rawData, "ephemeral_5m_input_tokens", value); } } + /// public override void Validate() { _ = this.Ephemeral1hInputTokens; @@ -74,6 +37,9 @@ public override void Validate() public BetaCacheCreation() { } + public BetaCacheCreation(BetaCacheCreation betaCacheCreation) + : base(betaCacheCreation) { } + public BetaCacheCreation(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -87,6 +53,7 @@ public BetaCacheCreation(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaCacheCreation FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -97,6 +64,7 @@ IReadOnlyDictionary rawData class BetaCacheCreationFromRaw : IFromRaw { + /// public BetaCacheCreation FromRawUnchecked(IReadOnlyDictionary rawData) => BetaCacheCreation.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaCitationCharLocation.cs b/src/Anthropic/Models/Beta/Messages/BetaCitationCharLocation.cs index 6fd035e1..d3afd6cb 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCitationCharLocation.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCitationCharLocation.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,149 +13,47 @@ public sealed record class BetaCitationCharLocation : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long DocumentIndex { - get - { - if (!this._rawData.TryGetValue("document_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'document_index' cannot be null", - new ArgumentOutOfRangeException("document_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "document_index"); } + init { ModelBase.Set(this._rawData, "document_index", value); } } public required string? DocumentTitle { - get - { - if (!this._rawData.TryGetValue("document_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "document_title"); } + init { ModelBase.Set(this._rawData, "document_title", value); } } public required long EndCharIndex { - get - { - if (!this._rawData.TryGetValue("end_char_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_char_index' cannot be null", - new ArgumentOutOfRangeException("end_char_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_char_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_char_index"); } + init { ModelBase.Set(this._rawData, "end_char_index", value); } } public required string? FileID { - get - { - if (!this._rawData.TryGetValue("file_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["file_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "file_id"); } + init { ModelBase.Set(this._rawData, "file_id", value); } } public required long StartCharIndex { - get - { - if (!this._rawData.TryGetValue("start_char_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_char_index' cannot be null", - new ArgumentOutOfRangeException("start_char_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_char_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_char_index"); } + init { ModelBase.Set(this._rawData, "start_char_index", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -181,6 +78,9 @@ public BetaCitationCharLocation() this.Type = JsonSerializer.Deserialize("\"char_location\""); } + public BetaCitationCharLocation(BetaCitationCharLocation betaCitationCharLocation) + : base(betaCitationCharLocation) { } + public BetaCitationCharLocation(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -196,6 +96,7 @@ public BetaCitationCharLocation(IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaCitationCharLocation FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -206,6 +107,7 @@ IReadOnlyDictionary rawData class BetaCitationCharLocationFromRaw : IFromRaw { + /// public BetaCitationCharLocation FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCitationCharLocation.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCitationCharLocationParam.cs b/src/Anthropic/Models/Beta/Messages/BetaCitationCharLocationParam.cs index 029c10a9..e594bec1 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCitationCharLocationParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCitationCharLocationParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,131 +15,41 @@ public sealed record class BetaCitationCharLocationParam : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long DocumentIndex { - get - { - if (!this._rawData.TryGetValue("document_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'document_index' cannot be null", - new ArgumentOutOfRangeException("document_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "document_index"); } + init { ModelBase.Set(this._rawData, "document_index", value); } } public required string? DocumentTitle { - get - { - if (!this._rawData.TryGetValue("document_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "document_title"); } + init { ModelBase.Set(this._rawData, "document_title", value); } } public required long EndCharIndex { - get - { - if (!this._rawData.TryGetValue("end_char_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_char_index' cannot be null", - new ArgumentOutOfRangeException("end_char_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_char_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_char_index"); } + init { ModelBase.Set(this._rawData, "end_char_index", value); } } public required long StartCharIndex { - get - { - if (!this._rawData.TryGetValue("start_char_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_char_index' cannot be null", - new ArgumentOutOfRangeException("start_char_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_char_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_char_index"); } + init { ModelBase.Set(this._rawData, "start_char_index", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -164,6 +73,11 @@ public BetaCitationCharLocationParam() this.Type = JsonSerializer.Deserialize("\"char_location\""); } + public BetaCitationCharLocationParam( + BetaCitationCharLocationParam betaCitationCharLocationParam + ) + : base(betaCitationCharLocationParam) { } + public BetaCitationCharLocationParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -179,6 +93,7 @@ public BetaCitationCharLocationParam(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaCitationCharLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -189,6 +104,7 @@ IReadOnlyDictionary rawData class BetaCitationCharLocationParamFromRaw : IFromRaw { + /// public BetaCitationCharLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCitationCharLocationParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCitationConfig.cs b/src/Anthropic/Models/Beta/Messages/BetaCitationConfig.cs index 077d71ae..c9dddc95 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCitationConfig.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCitationConfig.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Messages; @@ -14,25 +12,11 @@ public sealed record class BetaCitationConfig : ModelBase { public required bool Enabled { - get - { - if (!this._rawData.TryGetValue("enabled", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'enabled' cannot be null", - new ArgumentOutOfRangeException("enabled", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["enabled"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "enabled"); } + init { ModelBase.Set(this._rawData, "enabled", value); } } + /// public override void Validate() { _ = this.Enabled; @@ -40,6 +24,9 @@ public override void Validate() public BetaCitationConfig() { } + public BetaCitationConfig(BetaCitationConfig betaCitationConfig) + : base(betaCitationConfig) { } + public BetaCitationConfig(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -53,6 +40,7 @@ public BetaCitationConfig(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaCitationConfig FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -70,6 +58,7 @@ public BetaCitationConfig(bool enabled) class BetaCitationConfigFromRaw : IFromRaw { + /// public BetaCitationConfig FromRawUnchecked(IReadOnlyDictionary rawData) => BetaCitationConfig.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaCitationContentBlockLocation.cs b/src/Anthropic/Models/Beta/Messages/BetaCitationContentBlockLocation.cs index a2901f68..02fd3833 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCitationContentBlockLocation.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCitationContentBlockLocation.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,152 +18,47 @@ public sealed record class BetaCitationContentBlockLocation : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long DocumentIndex { - get - { - if (!this._rawData.TryGetValue("document_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'document_index' cannot be null", - new ArgumentOutOfRangeException("document_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "document_index"); } + init { ModelBase.Set(this._rawData, "document_index", value); } } public required string? DocumentTitle { - get - { - if (!this._rawData.TryGetValue("document_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "document_title"); } + init { ModelBase.Set(this._rawData, "document_title", value); } } public required long EndBlockIndex { - get - { - if (!this._rawData.TryGetValue("end_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_block_index' cannot be null", - new ArgumentOutOfRangeException("end_block_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_block_index"); } + init { ModelBase.Set(this._rawData, "end_block_index", value); } } public required string? FileID { - get - { - if (!this._rawData.TryGetValue("file_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["file_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "file_id"); } + init { ModelBase.Set(this._rawData, "file_id", value); } } public required long StartBlockIndex { - get - { - if (!this._rawData.TryGetValue("start_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_block_index' cannot be null", - new ArgumentOutOfRangeException( - "start_block_index", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_block_index"); } + init { ModelBase.Set(this._rawData, "start_block_index", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -189,6 +83,11 @@ public BetaCitationContentBlockLocation() this.Type = JsonSerializer.Deserialize("\"content_block_location\""); } + public BetaCitationContentBlockLocation( + BetaCitationContentBlockLocation betaCitationContentBlockLocation + ) + : base(betaCitationContentBlockLocation) { } + public BetaCitationContentBlockLocation(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -204,6 +103,7 @@ public BetaCitationContentBlockLocation(IReadOnlyDictionary } #pragma warning restore CS8618 + /// public static BetaCitationContentBlockLocation FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -214,6 +114,7 @@ IReadOnlyDictionary rawData class BetaCitationContentBlockLocationFromRaw : IFromRaw { + /// public BetaCitationContentBlockLocation FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCitationContentBlockLocation.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCitationContentBlockLocationParam.cs b/src/Anthropic/Models/Beta/Messages/BetaCitationContentBlockLocationParam.cs index 461eb1fe..a6a82425 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCitationContentBlockLocationParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCitationContentBlockLocationParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,134 +18,41 @@ public sealed record class BetaCitationContentBlockLocationParam : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long DocumentIndex { - get - { - if (!this._rawData.TryGetValue("document_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'document_index' cannot be null", - new ArgumentOutOfRangeException("document_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "document_index"); } + init { ModelBase.Set(this._rawData, "document_index", value); } } public required string? DocumentTitle { - get - { - if (!this._rawData.TryGetValue("document_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "document_title"); } + init { ModelBase.Set(this._rawData, "document_title", value); } } public required long EndBlockIndex { - get - { - if (!this._rawData.TryGetValue("end_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_block_index' cannot be null", - new ArgumentOutOfRangeException("end_block_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_block_index"); } + init { ModelBase.Set(this._rawData, "end_block_index", value); } } public required long StartBlockIndex { - get - { - if (!this._rawData.TryGetValue("start_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_block_index' cannot be null", - new ArgumentOutOfRangeException( - "start_block_index", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_block_index"); } + init { ModelBase.Set(this._rawData, "start_block_index", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -170,6 +76,11 @@ public BetaCitationContentBlockLocationParam() this.Type = JsonSerializer.Deserialize("\"content_block_location\""); } + public BetaCitationContentBlockLocationParam( + BetaCitationContentBlockLocationParam betaCitationContentBlockLocationParam + ) + : base(betaCitationContentBlockLocationParam) { } + public BetaCitationContentBlockLocationParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -185,6 +96,7 @@ public BetaCitationContentBlockLocationParam(IReadOnlyDictionary public static BetaCitationContentBlockLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -195,6 +107,7 @@ IReadOnlyDictionary rawData class BetaCitationContentBlockLocationParamFromRaw : IFromRaw { + /// public BetaCitationContentBlockLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCitationContentBlockLocationParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCitationPageLocation.cs b/src/Anthropic/Models/Beta/Messages/BetaCitationPageLocation.cs index 176e4978..9755d015 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCitationPageLocation.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCitationPageLocation.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,152 +13,47 @@ public sealed record class BetaCitationPageLocation : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long DocumentIndex { - get - { - if (!this._rawData.TryGetValue("document_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'document_index' cannot be null", - new ArgumentOutOfRangeException("document_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "document_index"); } + init { ModelBase.Set(this._rawData, "document_index", value); } } public required string? DocumentTitle { - get - { - if (!this._rawData.TryGetValue("document_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "document_title"); } + init { ModelBase.Set(this._rawData, "document_title", value); } } public required long EndPageNumber { - get - { - if (!this._rawData.TryGetValue("end_page_number", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_page_number' cannot be null", - new ArgumentOutOfRangeException("end_page_number", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_page_number"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_page_number"); } + init { ModelBase.Set(this._rawData, "end_page_number", value); } } public required string? FileID { - get - { - if (!this._rawData.TryGetValue("file_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["file_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "file_id"); } + init { ModelBase.Set(this._rawData, "file_id", value); } } public required long StartPageNumber { - get - { - if (!this._rawData.TryGetValue("start_page_number", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_page_number' cannot be null", - new ArgumentOutOfRangeException( - "start_page_number", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_page_number"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_page_number"); } + init { ModelBase.Set(this._rawData, "start_page_number", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -184,6 +78,9 @@ public BetaCitationPageLocation() this.Type = JsonSerializer.Deserialize("\"page_location\""); } + public BetaCitationPageLocation(BetaCitationPageLocation betaCitationPageLocation) + : base(betaCitationPageLocation) { } + public BetaCitationPageLocation(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -199,6 +96,7 @@ public BetaCitationPageLocation(IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaCitationPageLocation FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -209,6 +107,7 @@ IReadOnlyDictionary rawData class BetaCitationPageLocationFromRaw : IFromRaw { + /// public BetaCitationPageLocation FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCitationPageLocation.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCitationPageLocationParam.cs b/src/Anthropic/Models/Beta/Messages/BetaCitationPageLocationParam.cs index c168411b..e2816393 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCitationPageLocationParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCitationPageLocationParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,134 +15,41 @@ public sealed record class BetaCitationPageLocationParam : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long DocumentIndex { - get - { - if (!this._rawData.TryGetValue("document_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'document_index' cannot be null", - new ArgumentOutOfRangeException("document_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "document_index"); } + init { ModelBase.Set(this._rawData, "document_index", value); } } public required string? DocumentTitle { - get - { - if (!this._rawData.TryGetValue("document_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "document_title"); } + init { ModelBase.Set(this._rawData, "document_title", value); } } public required long EndPageNumber { - get - { - if (!this._rawData.TryGetValue("end_page_number", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_page_number' cannot be null", - new ArgumentOutOfRangeException("end_page_number", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_page_number"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_page_number"); } + init { ModelBase.Set(this._rawData, "end_page_number", value); } } public required long StartPageNumber { - get - { - if (!this._rawData.TryGetValue("start_page_number", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_page_number' cannot be null", - new ArgumentOutOfRangeException( - "start_page_number", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_page_number"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_page_number"); } + init { ModelBase.Set(this._rawData, "start_page_number", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -167,6 +73,11 @@ public BetaCitationPageLocationParam() this.Type = JsonSerializer.Deserialize("\"page_location\""); } + public BetaCitationPageLocationParam( + BetaCitationPageLocationParam betaCitationPageLocationParam + ) + : base(betaCitationPageLocationParam) { } + public BetaCitationPageLocationParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -182,6 +93,7 @@ public BetaCitationPageLocationParam(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaCitationPageLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -192,6 +104,7 @@ IReadOnlyDictionary rawData class BetaCitationPageLocationParamFromRaw : IFromRaw { + /// public BetaCitationPageLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCitationPageLocationParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCitationSearchResultLocation.cs b/src/Anthropic/Models/Beta/Messages/BetaCitationSearchResultLocation.cs index 99ca3801..42f58896 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCitationSearchResultLocation.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCitationSearchResultLocation.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,162 +18,47 @@ public sealed record class BetaCitationSearchResultLocation : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long EndBlockIndex { - get - { - if (!this._rawData.TryGetValue("end_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_block_index' cannot be null", - new ArgumentOutOfRangeException("end_block_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_block_index"); } + init { ModelBase.Set(this._rawData, "end_block_index", value); } } public required long SearchResultIndex { - get - { - if (!this._rawData.TryGetValue("search_result_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'search_result_index' cannot be null", - new ArgumentOutOfRangeException( - "search_result_index", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["search_result_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "search_result_index"); } + init { ModelBase.Set(this._rawData, "search_result_index", value); } } public required string Source { - get - { - if (!this._rawData.TryGetValue("source", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentOutOfRangeException("source", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentNullException("source") - ); - } - init - { - this._rawData["source"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "source"); } + init { ModelBase.Set(this._rawData, "source", value); } } public required long StartBlockIndex { - get - { - if (!this._rawData.TryGetValue("start_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_block_index' cannot be null", - new ArgumentOutOfRangeException( - "start_block_index", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_block_index"); } + init { ModelBase.Set(this._rawData, "start_block_index", value); } } public required string? Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -199,6 +83,11 @@ public BetaCitationSearchResultLocation() this.Type = JsonSerializer.Deserialize("\"search_result_location\""); } + public BetaCitationSearchResultLocation( + BetaCitationSearchResultLocation betaCitationSearchResultLocation + ) + : base(betaCitationSearchResultLocation) { } + public BetaCitationSearchResultLocation(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -214,6 +103,7 @@ public BetaCitationSearchResultLocation(IReadOnlyDictionary } #pragma warning restore CS8618 + /// public static BetaCitationSearchResultLocation FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -224,6 +114,7 @@ IReadOnlyDictionary rawData class BetaCitationSearchResultLocationFromRaw : IFromRaw { + /// public BetaCitationSearchResultLocation FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCitationSearchResultLocation.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCitationSearchResultLocationParam.cs b/src/Anthropic/Models/Beta/Messages/BetaCitationSearchResultLocationParam.cs index 507b2cbf..68a6ed2f 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCitationSearchResultLocationParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCitationSearchResultLocationParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,162 +18,47 @@ public sealed record class BetaCitationSearchResultLocationParam : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long EndBlockIndex { - get - { - if (!this._rawData.TryGetValue("end_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_block_index' cannot be null", - new ArgumentOutOfRangeException("end_block_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_block_index"); } + init { ModelBase.Set(this._rawData, "end_block_index", value); } } public required long SearchResultIndex { - get - { - if (!this._rawData.TryGetValue("search_result_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'search_result_index' cannot be null", - new ArgumentOutOfRangeException( - "search_result_index", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["search_result_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "search_result_index"); } + init { ModelBase.Set(this._rawData, "search_result_index", value); } } public required string Source { - get - { - if (!this._rawData.TryGetValue("source", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentOutOfRangeException("source", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentNullException("source") - ); - } - init - { - this._rawData["source"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "source"); } + init { ModelBase.Set(this._rawData, "source", value); } } public required long StartBlockIndex { - get - { - if (!this._rawData.TryGetValue("start_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_block_index' cannot be null", - new ArgumentOutOfRangeException( - "start_block_index", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_block_index"); } + init { ModelBase.Set(this._rawData, "start_block_index", value); } } public required string? Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -199,6 +83,11 @@ public BetaCitationSearchResultLocationParam() this.Type = JsonSerializer.Deserialize("\"search_result_location\""); } + public BetaCitationSearchResultLocationParam( + BetaCitationSearchResultLocationParam betaCitationSearchResultLocationParam + ) + : base(betaCitationSearchResultLocationParam) { } + public BetaCitationSearchResultLocationParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -214,6 +103,7 @@ public BetaCitationSearchResultLocationParam(IReadOnlyDictionary public static BetaCitationSearchResultLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -224,6 +114,7 @@ IReadOnlyDictionary rawData class BetaCitationSearchResultLocationParamFromRaw : IFromRaw { + /// public BetaCitationSearchResultLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCitationSearchResultLocationParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCitationWebSearchResultLocationParam.cs b/src/Anthropic/Models/Beta/Messages/BetaCitationWebSearchResultLocationParam.cs index 94a2e154..2fc9b40b 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCitationWebSearchResultLocationParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCitationWebSearchResultLocationParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,118 +18,35 @@ public sealed record class BetaCitationWebSearchResultLocationParam : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required string EncryptedIndex { - get - { - if (!this._rawData.TryGetValue("encrypted_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'encrypted_index' cannot be null", - new ArgumentOutOfRangeException("encrypted_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'encrypted_index' cannot be null", - new ArgumentNullException("encrypted_index") - ); - } - init - { - this._rawData["encrypted_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "encrypted_index"); } + init { ModelBase.Set(this._rawData, "encrypted_index", value); } } public required string? Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required string URL { - get - { - if (!this._rawData.TryGetValue("url", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentOutOfRangeException("url", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentNullException("url") - ); - } - init - { - this._rawData["url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "url"); } + init { ModelBase.Set(this._rawData, "url", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -153,6 +69,11 @@ public BetaCitationWebSearchResultLocationParam() this.Type = JsonSerializer.Deserialize("\"web_search_result_location\""); } + public BetaCitationWebSearchResultLocationParam( + BetaCitationWebSearchResultLocationParam betaCitationWebSearchResultLocationParam + ) + : base(betaCitationWebSearchResultLocationParam) { } + public BetaCitationWebSearchResultLocationParam( IReadOnlyDictionary rawData ) @@ -170,6 +91,7 @@ IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaCitationWebSearchResultLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -181,6 +103,7 @@ IReadOnlyDictionary rawData class BetaCitationWebSearchResultLocationParamFromRaw : IFromRaw { + /// public BetaCitationWebSearchResultLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCitationWebSearchResultLocationParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCitationsConfigParam.cs b/src/Anthropic/Models/Beta/Messages/BetaCitationsConfigParam.cs index a8de787a..eb0a3245 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCitationsConfigParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCitationsConfigParam.cs @@ -12,13 +12,7 @@ public sealed record class BetaCitationsConfigParam : ModelBase { public bool? Enabled { - get - { - if (!this._rawData.TryGetValue("enabled", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "enabled"); } init { if (value == null) @@ -26,13 +20,11 @@ public bool? Enabled return; } - this._rawData["enabled"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "enabled", value); } } + /// public override void Validate() { _ = this.Enabled; @@ -40,6 +32,9 @@ public override void Validate() public BetaCitationsConfigParam() { } + public BetaCitationsConfigParam(BetaCitationsConfigParam betaCitationsConfigParam) + : base(betaCitationsConfigParam) { } + public BetaCitationsConfigParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -53,6 +48,7 @@ public BetaCitationsConfigParam(IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaCitationsConfigParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -63,6 +59,7 @@ IReadOnlyDictionary rawData class BetaCitationsConfigParamFromRaw : IFromRaw { + /// public BetaCitationsConfigParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCitationsConfigParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCitationsDelta.cs b/src/Anthropic/Models/Beta/Messages/BetaCitationsDelta.cs index 8ef0da2c..f209f6f1 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCitationsDelta.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCitationsDelta.cs @@ -14,50 +14,17 @@ public sealed record class BetaCitationsDelta : ModelBase { public required Citation Citation { - get - { - if (!this._rawData.TryGetValue("citation", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'citation' cannot be null", - new System::ArgumentOutOfRangeException("citation", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'citation' cannot be null", - new System::ArgumentNullException("citation") - ); - } - init - { - this._rawData["citation"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "citation"); } + init { ModelBase.Set(this._rawData, "citation", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Citation.Validate(); @@ -77,6 +44,9 @@ public BetaCitationsDelta() this.Type = JsonSerializer.Deserialize("\"citations_delta\""); } + public BetaCitationsDelta(BetaCitationsDelta betaCitationsDelta) + : base(betaCitationsDelta) { } + public BetaCitationsDelta(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +62,7 @@ public BetaCitationsDelta(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaCitationsDelta FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +80,7 @@ public BetaCitationsDelta(Citation citation) class BetaCitationsDeltaFromRaw : IFromRaw { + /// public BetaCitationsDelta FromRawUnchecked(IReadOnlyDictionary rawData) => BetaCitationsDelta.FromRawUnchecked(rawData); } @@ -272,6 +244,21 @@ public Citation(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaCitationCharLocation(out var value)) { + /// // `value` is of type `BetaCitationCharLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaCitationCharLocation( [NotNullWhen(true)] out BetaCitationCharLocation? value ) @@ -280,6 +267,21 @@ public bool TryPickBetaCitationCharLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaCitationPageLocation(out var value)) { + /// // `value` is of type `BetaCitationPageLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaCitationPageLocation( [NotNullWhen(true)] out BetaCitationPageLocation? value ) @@ -288,6 +290,21 @@ public bool TryPickBetaCitationPageLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaCitationContentBlockLocation(out var value)) { + /// // `value` is of type `BetaCitationContentBlockLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaCitationContentBlockLocation( [NotNullWhen(true)] out BetaCitationContentBlockLocation? value ) @@ -296,6 +313,21 @@ public bool TryPickBetaCitationContentBlockLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaCitationsWebSearchResultLocation(out var value)) { + /// // `value` is of type `BetaCitationsWebSearchResultLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaCitationsWebSearchResultLocation( [NotNullWhen(true)] out BetaCitationsWebSearchResultLocation? value ) @@ -304,6 +336,21 @@ public bool TryPickBetaCitationsWebSearchResultLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaCitationSearchResultLocation(out var value)) { + /// // `value` is of type `BetaCitationSearchResultLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaCitationSearchResultLocation( [NotNullWhen(true)] out BetaCitationSearchResultLocation? value ) @@ -312,6 +359,29 @@ public bool TryPickBetaCitationSearchResultLocation( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaCitationCharLocation value) => {...}, + /// (BetaCitationPageLocation value) => {...}, + /// (BetaCitationContentBlockLocation value) => {...}, + /// (BetaCitationsWebSearchResultLocation value) => {...}, + /// (BetaCitationSearchResultLocation value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaCitationCharLocation, System::Action betaCitationPageLocation, @@ -344,6 +414,30 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaCitationCharLocation value) => {...}, + /// (BetaCitationPageLocation value) => {...}, + /// (BetaCitationContentBlockLocation value) => {...}, + /// (BetaCitationsWebSearchResultLocation value) => {...}, + /// (BetaCitationSearchResultLocation value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaCitationCharLocation, System::Func betaCitationPageLocation, @@ -378,12 +472,40 @@ public static implicit operator Citation(BetaCitationsWebSearchResultLocation va public static implicit operator Citation(BetaCitationSearchResultLocation value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of Citation"); } + this.Switch( + (betaCitationCharLocation) => betaCitationCharLocation.Validate(), + (betaCitationPageLocation) => betaCitationPageLocation.Validate(), + (betaCitationContentBlockLocation) => betaCitationContentBlockLocation.Validate(), + (betaCitationsWebSearchResultLocation) => + betaCitationsWebSearchResultLocation.Validate(), + (betaCitationSearchResultLocation) => betaCitationSearchResultLocation.Validate() + ); + } + + public virtual bool Equals(Citation? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaCitationsWebSearchResultLocation.cs b/src/Anthropic/Models/Beta/Messages/BetaCitationsWebSearchResultLocation.cs index 97a440a4..7fda6cbb 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCitationsWebSearchResultLocation.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCitationsWebSearchResultLocation.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,118 +18,35 @@ public sealed record class BetaCitationsWebSearchResultLocation : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required string EncryptedIndex { - get - { - if (!this._rawData.TryGetValue("encrypted_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'encrypted_index' cannot be null", - new ArgumentOutOfRangeException("encrypted_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'encrypted_index' cannot be null", - new ArgumentNullException("encrypted_index") - ); - } - init - { - this._rawData["encrypted_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "encrypted_index"); } + init { ModelBase.Set(this._rawData, "encrypted_index", value); } } public required string? Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required string URL { - get - { - if (!this._rawData.TryGetValue("url", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentOutOfRangeException("url", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentNullException("url") - ); - } - init - { - this._rawData["url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "url"); } + init { ModelBase.Set(this._rawData, "url", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -153,6 +69,11 @@ public BetaCitationsWebSearchResultLocation() this.Type = JsonSerializer.Deserialize("\"web_search_result_location\""); } + public BetaCitationsWebSearchResultLocation( + BetaCitationsWebSearchResultLocation betaCitationsWebSearchResultLocation + ) + : base(betaCitationsWebSearchResultLocation) { } + public BetaCitationsWebSearchResultLocation(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -168,6 +89,7 @@ public BetaCitationsWebSearchResultLocation(IReadOnlyDictionary public static BetaCitationsWebSearchResultLocation FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -178,6 +100,7 @@ IReadOnlyDictionary rawData class BetaCitationsWebSearchResultLocationFromRaw : IFromRaw { + /// public BetaCitationsWebSearchResultLocation FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCitationsWebSearchResultLocation.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaClearThinking20251015Edit.cs b/src/Anthropic/Models/Beta/Messages/BetaClearThinking20251015Edit.cs index d0d0a160..75a7897e 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaClearThinking20251015Edit.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaClearThinking20251015Edit.cs @@ -16,23 +16,8 @@ public sealed record class BetaClearThinking20251015Edit : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -41,13 +26,7 @@ public JsonElement Type /// public Keep? Keep { - get - { - if (!this._rawData.TryGetValue("keep", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawData, "keep"); } init { if (value == null) @@ -55,13 +34,11 @@ public Keep? Keep return; } - this._rawData["keep"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "keep", value); } } + /// public override void Validate() { if ( @@ -81,6 +58,11 @@ public BetaClearThinking20251015Edit() this.Type = JsonSerializer.Deserialize("\"clear_thinking_20251015\""); } + public BetaClearThinking20251015Edit( + BetaClearThinking20251015Edit betaClearThinking20251015Edit + ) + : base(betaClearThinking20251015Edit) { } + public BetaClearThinking20251015Edit(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -96,6 +78,7 @@ public BetaClearThinking20251015Edit(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaClearThinking20251015Edit FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -106,6 +89,7 @@ IReadOnlyDictionary rawData class BetaClearThinking20251015EditFromRaw : IFromRaw { + /// public BetaClearThinking20251015Edit FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaClearThinking20251015Edit.FromRawUnchecked(rawData); @@ -162,24 +146,90 @@ public Keep(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaThinkingTurns(out var value)) { + /// // `value` is of type `BetaThinkingTurns` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaThinkingTurns([NotNullWhen(true)] out BetaThinkingTurns? value) { value = this.Value as BetaThinkingTurns; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaAllThinkingTurns(out var value)) { + /// // `value` is of type `BetaAllThinkingTurns` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaAllThinkingTurns([NotNullWhen(true)] out BetaAllThinkingTurns? value) { value = this.Value as BetaAllThinkingTurns; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickAll(out var value)) { + /// // `value` is of type `UnionMember2` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickAll([NotNullWhen(true)] out UnionMember2? value) { value = this.Value as UnionMember2; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaThinkingTurns value) => {...}, + /// (BetaAllThinkingTurns value) => {...}, + /// (UnionMember2 value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaThinkingTurns, System::Action betaAllThinkingTurns, @@ -202,6 +252,28 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaThinkingTurns value) => {...}, + /// (BetaAllThinkingTurns value) => {...}, + /// (UnionMember2 value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaThinkingTurns, System::Func betaAllThinkingTurns, @@ -223,12 +295,37 @@ public T Match( public static implicit operator Keep(UnionMember2 value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of Keep"); } + this.Switch( + (betaThinkingTurns) => betaThinkingTurns.Validate(), + (betaAllThinkingTurns) => betaAllThinkingTurns.Validate(), + (all) => all.Validate() + ); + } + + public virtual bool Equals(Keep? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } @@ -293,7 +390,7 @@ public override void Write(Utf8JsonWriter writer, Keep value, JsonSerializerOpti } [JsonConverter(typeof(Converter))] -public class UnionMember2 +public record class UnionMember2 { public JsonElement Json { get; private init; } @@ -307,14 +404,38 @@ public UnionMember2() Json = json; } + /// + /// Validates that the instance's underlying value is the expected constant. + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { - if (JsonElement.DeepEquals(this.Json, new UnionMember2().Json)) + if (this != new UnionMember2()) { throw new AnthropicInvalidDataException("Invalid value given for 'UnionMember2'"); } } + public override int GetHashCode() + { + return 0; + } + + public virtual bool Equals(UnionMember2? other) + { + if (other == null) + { + return false; + } + + return JsonElement.DeepEquals(this.Json, other.Json); + } + class Converter : JsonConverter { public override UnionMember2? Read( diff --git a/src/Anthropic/Models/Beta/Messages/BetaClearThinking20251015EditResponse.cs b/src/Anthropic/Models/Beta/Messages/BetaClearThinking20251015EditResponse.cs index aa57fc25..c7cf3f8b 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaClearThinking20251015EditResponse.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaClearThinking20251015EditResponse.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -22,26 +21,8 @@ public sealed record class BetaClearThinking20251015EditResponse : ModelBase /// public required long ClearedInputTokens { - get - { - if (!this._rawData.TryGetValue("cleared_input_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cleared_input_tokens' cannot be null", - new ArgumentOutOfRangeException( - "cleared_input_tokens", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["cleared_input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "cleared_input_tokens"); } + init { ModelBase.Set(this._rawData, "cleared_input_tokens", value); } } /// @@ -49,26 +30,8 @@ public required long ClearedInputTokens /// public required long ClearedThinkingTurns { - get - { - if (!this._rawData.TryGetValue("cleared_thinking_turns", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cleared_thinking_turns' cannot be null", - new ArgumentOutOfRangeException( - "cleared_thinking_turns", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["cleared_thinking_turns"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "cleared_thinking_turns"); } + init { ModelBase.Set(this._rawData, "cleared_thinking_turns", value); } } /// @@ -76,25 +39,11 @@ public required long ClearedThinkingTurns /// public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ClearedInputTokens; @@ -115,6 +64,11 @@ public BetaClearThinking20251015EditResponse() this.Type = JsonSerializer.Deserialize("\"clear_thinking_20251015\""); } + public BetaClearThinking20251015EditResponse( + BetaClearThinking20251015EditResponse betaClearThinking20251015EditResponse + ) + : base(betaClearThinking20251015EditResponse) { } + public BetaClearThinking20251015EditResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -130,6 +84,7 @@ public BetaClearThinking20251015EditResponse(IReadOnlyDictionary public static BetaClearThinking20251015EditResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -140,6 +95,7 @@ IReadOnlyDictionary rawData class BetaClearThinking20251015EditResponseFromRaw : IFromRaw { + /// public BetaClearThinking20251015EditResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaClearThinking20251015EditResponse.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaClearToolUses20250919Edit.cs b/src/Anthropic/Models/Beta/Messages/BetaClearToolUses20250919Edit.cs index 034b00fb..0adaa291 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaClearToolUses20250919Edit.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaClearToolUses20250919Edit.cs @@ -17,23 +17,8 @@ public sealed record class BetaClearToolUses20250919Edit : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -44,21 +29,12 @@ public BetaInputTokensClearAtLeast? ClearAtLeast { get { - if (!this._rawData.TryGetValue("clear_at_least", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["clear_at_least"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "clear_at_least" ); } + init { ModelBase.Set(this._rawData, "clear_at_least", value); } } /// @@ -68,21 +44,9 @@ public ClearToolInputs? ClearToolInputs { get { - if (!this._rawData.TryGetValue("clear_tool_inputs", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["clear_tool_inputs"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "clear_tool_inputs"); } + init { ModelBase.Set(this._rawData, "clear_tool_inputs", value); } } /// @@ -90,20 +54,8 @@ public ClearToolInputs? ClearToolInputs /// public IReadOnlyList? ExcludeTools { - get - { - if (!this._rawData.TryGetValue("exclude_tools", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["exclude_tools"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "exclude_tools"); } + init { ModelBase.Set(this._rawData, "exclude_tools", value); } } /// @@ -111,16 +63,7 @@ public IReadOnlyList? ExcludeTools /// public BetaToolUsesKeep? Keep { - get - { - if (!this._rawData.TryGetValue("keep", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "keep"); } init { if (value == null) @@ -128,10 +71,7 @@ public BetaToolUsesKeep? Keep return; } - this._rawData["keep"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "keep", value); } } @@ -140,13 +80,7 @@ public BetaToolUsesKeep? Keep /// public Trigger? Trigger { - get - { - if (!this._rawData.TryGetValue("trigger", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawData, "trigger"); } init { if (value == null) @@ -154,13 +88,11 @@ public Trigger? Trigger return; } - this._rawData["trigger"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "trigger", value); } } + /// public override void Validate() { if ( @@ -184,6 +116,11 @@ public BetaClearToolUses20250919Edit() this.Type = JsonSerializer.Deserialize("\"clear_tool_uses_20250919\""); } + public BetaClearToolUses20250919Edit( + BetaClearToolUses20250919Edit betaClearToolUses20250919Edit + ) + : base(betaClearToolUses20250919Edit) { } + public BetaClearToolUses20250919Edit(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -199,6 +136,7 @@ public BetaClearToolUses20250919Edit(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaClearToolUses20250919Edit FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -209,6 +147,7 @@ IReadOnlyDictionary rawData class BetaClearToolUses20250919EditFromRaw : IFromRaw { + /// public BetaClearToolUses20250919Edit FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaClearToolUses20250919Edit.FromRawUnchecked(rawData); @@ -246,18 +185,68 @@ public ClearToolInputs(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBool(out var value)) { + /// // `value` is of type `bool` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBool([NotNullWhen(true)] out bool? value) { value = this.Value as bool?; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickStrings(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickStrings([NotNullWhen(true)] out IReadOnlyList? value) { value = this.Value as IReadOnlyList; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (bool value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch(System::Action @bool, System::Action> strings) { switch (this.Value) @@ -275,6 +264,27 @@ public void Switch(System::Action @bool, System::Action + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (bool value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match(System::Func @bool, System::Func, T> strings) { return this.Value switch @@ -292,6 +302,16 @@ public T Match(System::Func @bool, System::Func value) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -301,6 +321,16 @@ public void Validate() ); } } + + public virtual bool Equals(ClearToolInputs? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } } sealed class ClearToolInputsConverter : JsonConverter @@ -389,18 +419,68 @@ public Trigger(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaInputTokens(out var value)) { + /// // `value` is of type `BetaInputTokensTrigger` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaInputTokens([NotNullWhen(true)] out BetaInputTokensTrigger? value) { value = this.Value as BetaInputTokensTrigger; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolUses(out var value)) { + /// // `value` is of type `BetaToolUsesTrigger` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolUses([NotNullWhen(true)] out BetaToolUsesTrigger? value) { value = this.Value as BetaToolUsesTrigger; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaInputTokensTrigger value) => {...}, + /// (BetaToolUsesTrigger value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaInputTokens, System::Action betaToolUses @@ -421,6 +501,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaInputTokensTrigger value) => {...}, + /// (BetaToolUsesTrigger value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaInputTokens, System::Func betaToolUses @@ -440,12 +541,36 @@ public T Match( public static implicit operator Trigger(BetaToolUsesTrigger value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of Trigger"); } + this.Switch( + (betaInputTokens) => betaInputTokens.Validate(), + (betaToolUses) => betaToolUses.Validate() + ); + } + + public virtual bool Equals(Trigger? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaClearToolUses20250919EditResponse.cs b/src/Anthropic/Models/Beta/Messages/BetaClearToolUses20250919EditResponse.cs index a15406f4..723bb4f7 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaClearToolUses20250919EditResponse.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaClearToolUses20250919EditResponse.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -22,26 +21,8 @@ public sealed record class BetaClearToolUses20250919EditResponse : ModelBase /// public required long ClearedInputTokens { - get - { - if (!this._rawData.TryGetValue("cleared_input_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cleared_input_tokens' cannot be null", - new ArgumentOutOfRangeException( - "cleared_input_tokens", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["cleared_input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "cleared_input_tokens"); } + init { ModelBase.Set(this._rawData, "cleared_input_tokens", value); } } /// @@ -49,26 +30,8 @@ public required long ClearedInputTokens /// public required long ClearedToolUses { - get - { - if (!this._rawData.TryGetValue("cleared_tool_uses", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cleared_tool_uses' cannot be null", - new ArgumentOutOfRangeException( - "cleared_tool_uses", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["cleared_tool_uses"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "cleared_tool_uses"); } + init { ModelBase.Set(this._rawData, "cleared_tool_uses", value); } } /// @@ -76,25 +39,11 @@ public required long ClearedToolUses /// public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ClearedInputTokens; @@ -115,6 +64,11 @@ public BetaClearToolUses20250919EditResponse() this.Type = JsonSerializer.Deserialize("\"clear_tool_uses_20250919\""); } + public BetaClearToolUses20250919EditResponse( + BetaClearToolUses20250919EditResponse betaClearToolUses20250919EditResponse + ) + : base(betaClearToolUses20250919EditResponse) { } + public BetaClearToolUses20250919EditResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -130,6 +84,7 @@ public BetaClearToolUses20250919EditResponse(IReadOnlyDictionary public static BetaClearToolUses20250919EditResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -140,6 +95,7 @@ IReadOnlyDictionary rawData class BetaClearToolUses20250919EditResponseFromRaw : IFromRaw { + /// public BetaClearToolUses20250919EditResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaClearToolUses20250919EditResponse.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionOutputBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionOutputBlock.cs index 915122a4..bfe43255 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionOutputBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionOutputBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,50 +15,17 @@ public sealed record class BetaCodeExecutionOutputBlock : ModelBase { public required string FileID { - get - { - if (!this._rawData.TryGetValue("file_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentOutOfRangeException("file_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentNullException("file_id") - ); - } - init - { - this._rawData["file_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "file_id"); } + init { ModelBase.Set(this._rawData, "file_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.FileID; @@ -79,6 +45,9 @@ public BetaCodeExecutionOutputBlock() this.Type = JsonSerializer.Deserialize("\"code_execution_output\""); } + public BetaCodeExecutionOutputBlock(BetaCodeExecutionOutputBlock betaCodeExecutionOutputBlock) + : base(betaCodeExecutionOutputBlock) { } + public BetaCodeExecutionOutputBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -94,6 +63,7 @@ public BetaCodeExecutionOutputBlock(IReadOnlyDictionary raw } #pragma warning restore CS8618 + /// public static BetaCodeExecutionOutputBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -111,6 +81,7 @@ public BetaCodeExecutionOutputBlock(string fileID) class BetaCodeExecutionOutputBlockFromRaw : IFromRaw { + /// public BetaCodeExecutionOutputBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCodeExecutionOutputBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionOutputBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionOutputBlockParam.cs index 5fcf57e2..30e4dd7e 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionOutputBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionOutputBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,50 +18,17 @@ public sealed record class BetaCodeExecutionOutputBlockParam : ModelBase { public required string FileID { - get - { - if (!this._rawData.TryGetValue("file_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentOutOfRangeException("file_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentNullException("file_id") - ); - } - init - { - this._rawData["file_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "file_id"); } + init { ModelBase.Set(this._rawData, "file_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.FileID; @@ -82,6 +48,11 @@ public BetaCodeExecutionOutputBlockParam() this.Type = JsonSerializer.Deserialize("\"code_execution_output\""); } + public BetaCodeExecutionOutputBlockParam( + BetaCodeExecutionOutputBlockParam betaCodeExecutionOutputBlockParam + ) + : base(betaCodeExecutionOutputBlockParam) { } + public BetaCodeExecutionOutputBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -97,6 +68,7 @@ public BetaCodeExecutionOutputBlockParam(IReadOnlyDictionary public static BetaCodeExecutionOutputBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -114,6 +86,7 @@ public BetaCodeExecutionOutputBlockParam(string fileID) class BetaCodeExecutionOutputBlockParamFromRaw : IFromRaw { + /// public BetaCodeExecutionOutputBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCodeExecutionOutputBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionResultBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionResultBlock.cs index 1ab4ddad..14057cc2 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionResultBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionResultBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -18,122 +17,39 @@ public required IReadOnlyList Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required long ReturnCode { - get - { - if (!this._rawData.TryGetValue("return_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'return_code' cannot be null", - new ArgumentOutOfRangeException("return_code", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["return_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "return_code"); } + init { ModelBase.Set(this._rawData, "return_code", value); } } public required string Stderr { - get - { - if (!this._rawData.TryGetValue("stderr", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'stderr' cannot be null", - new ArgumentOutOfRangeException("stderr", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'stderr' cannot be null", - new ArgumentNullException("stderr") - ); - } - init - { - this._rawData["stderr"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "stderr"); } + init { ModelBase.Set(this._rawData, "stderr", value); } } public required string Stdout { - get - { - if (!this._rawData.TryGetValue("stdout", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'stdout' cannot be null", - new ArgumentOutOfRangeException("stdout", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'stdout' cannot be null", - new ArgumentNullException("stdout") - ); - } - init - { - this._rawData["stdout"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "stdout"); } + init { ModelBase.Set(this._rawData, "stdout", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { foreach (var item in this.Content) @@ -159,6 +75,9 @@ public BetaCodeExecutionResultBlock() this.Type = JsonSerializer.Deserialize("\"code_execution_result\""); } + public BetaCodeExecutionResultBlock(BetaCodeExecutionResultBlock betaCodeExecutionResultBlock) + : base(betaCodeExecutionResultBlock) { } + public BetaCodeExecutionResultBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -174,6 +93,7 @@ public BetaCodeExecutionResultBlock(IReadOnlyDictionary raw } #pragma warning restore CS8618 + /// public static BetaCodeExecutionResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -184,6 +104,7 @@ IReadOnlyDictionary rawData class BetaCodeExecutionResultBlockFromRaw : IFromRaw { + /// public BetaCodeExecutionResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCodeExecutionResultBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionResultBlockParam.cs index 7553d416..199745c4 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionResultBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -21,122 +20,39 @@ public required IReadOnlyList Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required long ReturnCode { - get - { - if (!this._rawData.TryGetValue("return_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'return_code' cannot be null", - new ArgumentOutOfRangeException("return_code", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["return_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "return_code"); } + init { ModelBase.Set(this._rawData, "return_code", value); } } public required string Stderr { - get - { - if (!this._rawData.TryGetValue("stderr", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'stderr' cannot be null", - new ArgumentOutOfRangeException("stderr", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'stderr' cannot be null", - new ArgumentNullException("stderr") - ); - } - init - { - this._rawData["stderr"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "stderr"); } + init { ModelBase.Set(this._rawData, "stderr", value); } } public required string Stdout { - get - { - if (!this._rawData.TryGetValue("stdout", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'stdout' cannot be null", - new ArgumentOutOfRangeException("stdout", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'stdout' cannot be null", - new ArgumentNullException("stdout") - ); - } - init - { - this._rawData["stdout"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "stdout"); } + init { ModelBase.Set(this._rawData, "stdout", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { foreach (var item in this.Content) @@ -162,6 +78,11 @@ public BetaCodeExecutionResultBlockParam() this.Type = JsonSerializer.Deserialize("\"code_execution_result\""); } + public BetaCodeExecutionResultBlockParam( + BetaCodeExecutionResultBlockParam betaCodeExecutionResultBlockParam + ) + : base(betaCodeExecutionResultBlockParam) { } + public BetaCodeExecutionResultBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -177,6 +98,7 @@ public BetaCodeExecutionResultBlockParam(IReadOnlyDictionary public static BetaCodeExecutionResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -187,6 +109,7 @@ IReadOnlyDictionary rawData class BetaCodeExecutionResultBlockParamFromRaw : IFromRaw { + /// public BetaCodeExecutionResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCodeExecutionResultBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionTool20250522.cs b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionTool20250522.cs index 7bcb2287..7c0abdb7 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionTool20250522.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionTool20250522.cs @@ -21,56 +21,23 @@ public sealed record class BetaCodeExecutionTool20250522 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public IReadOnlyList>? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawData, + "allowed_callers" ); } init @@ -80,10 +47,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -94,21 +58,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -117,13 +72,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -131,22 +80,13 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -154,13 +94,11 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } + /// public override void Validate() { if ( @@ -196,6 +134,11 @@ public BetaCodeExecutionTool20250522() this.Type = JsonSerializer.Deserialize("\"code_execution_20250522\""); } + public BetaCodeExecutionTool20250522( + BetaCodeExecutionTool20250522 betaCodeExecutionTool20250522 + ) + : base(betaCodeExecutionTool20250522) { } + public BetaCodeExecutionTool20250522(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -212,6 +155,7 @@ public BetaCodeExecutionTool20250522(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaCodeExecutionTool20250522 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -222,6 +166,7 @@ IReadOnlyDictionary rawData class BetaCodeExecutionTool20250522FromRaw : IFromRaw { + /// public BetaCodeExecutionTool20250522 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCodeExecutionTool20250522.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionTool20250825.cs b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionTool20250825.cs index fa8d1562..b9c54783 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionTool20250825.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionTool20250825.cs @@ -21,57 +21,25 @@ public sealed record class BetaCodeExecutionTool20250825 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList< + ApiEnum + >? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + List> + >(this.RawData, "allowed_callers"); } init { @@ -80,10 +48,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -94,21 +59,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -117,13 +73,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -131,22 +81,13 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -154,13 +95,11 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } + /// public override void Validate() { if ( @@ -196,6 +135,11 @@ public BetaCodeExecutionTool20250825() this.Type = JsonSerializer.Deserialize("\"code_execution_20250825\""); } + public BetaCodeExecutionTool20250825( + BetaCodeExecutionTool20250825 betaCodeExecutionTool20250825 + ) + : base(betaCodeExecutionTool20250825) { } + public BetaCodeExecutionTool20250825(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -212,6 +156,7 @@ public BetaCodeExecutionTool20250825(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaCodeExecutionTool20250825 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -222,21 +167,23 @@ IReadOnlyDictionary rawData class BetaCodeExecutionTool20250825FromRaw : IFromRaw { + /// public BetaCodeExecutionTool20250825 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCodeExecutionTool20250825.FromRawUnchecked(rawData); } -[JsonConverter(typeof(AllowedCallerModelConverter))] -public enum AllowedCallerModel +[JsonConverter(typeof(BetaCodeExecutionTool20250825AllowedCallerConverter))] +public enum BetaCodeExecutionTool20250825AllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCallerModelConverter : JsonConverter +sealed class BetaCodeExecutionTool20250825AllowedCallerConverter + : JsonConverter { - public override AllowedCallerModel Read( + public override BetaCodeExecutionTool20250825AllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -244,15 +191,16 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCallerModel.Direct, - "code_execution_20250825" => AllowedCallerModel.CodeExecution20250825, - _ => (AllowedCallerModel)(-1), + "direct" => BetaCodeExecutionTool20250825AllowedCaller.Direct, + "code_execution_20250825" => + BetaCodeExecutionTool20250825AllowedCaller.CodeExecution20250825, + _ => (BetaCodeExecutionTool20250825AllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCallerModel value, + BetaCodeExecutionTool20250825AllowedCaller value, JsonSerializerOptions options ) { @@ -260,8 +208,9 @@ JsonSerializerOptions options writer, value switch { - AllowedCallerModel.Direct => "direct", - AllowedCallerModel.CodeExecution20250825 => "code_execution_20250825", + BetaCodeExecutionTool20250825AllowedCaller.Direct => "direct", + BetaCodeExecutionTool20250825AllowedCaller.CodeExecution20250825 => + "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), diff --git a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlock.cs index 814e04f8..88fc508d 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -21,76 +20,27 @@ public required BetaCodeExecutionToolResultBlockContent Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new ArgumentOutOfRangeException("tool_use_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -111,6 +61,11 @@ public BetaCodeExecutionToolResultBlock() this.Type = JsonSerializer.Deserialize("\"code_execution_tool_result\""); } + public BetaCodeExecutionToolResultBlock( + BetaCodeExecutionToolResultBlock betaCodeExecutionToolResultBlock + ) + : base(betaCodeExecutionToolResultBlock) { } + public BetaCodeExecutionToolResultBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -126,6 +81,7 @@ public BetaCodeExecutionToolResultBlock(IReadOnlyDictionary } #pragma warning restore CS8618 + /// public static BetaCodeExecutionToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -136,6 +92,7 @@ IReadOnlyDictionary rawData class BetaCodeExecutionToolResultBlockFromRaw : IFromRaw { + /// public BetaCodeExecutionToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCodeExecutionToolResultBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlockContent.cs b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlockContent.cs index c1502887..59b7738e 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlockContent.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlockContent.cs @@ -46,18 +46,68 @@ public BetaCodeExecutionToolResultBlockContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickError(out var value)) { + /// // `value` is of type `BetaCodeExecutionToolResultError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickError([NotNullWhen(true)] out BetaCodeExecutionToolResultError? value) { value = this.Value as BetaCodeExecutionToolResultError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickResultBlock(out var value)) { + /// // `value` is of type `BetaCodeExecutionResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickResultBlock([NotNullWhen(true)] out BetaCodeExecutionResultBlock? value) { value = this.Value as BetaCodeExecutionResultBlock; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaCodeExecutionToolResultError value) => {...}, + /// (BetaCodeExecutionResultBlock value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action error, System::Action resultBlock @@ -78,6 +128,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaCodeExecutionToolResultError value) => {...}, + /// (BetaCodeExecutionResultBlock value) => {...} + /// ); + /// + /// + /// public T Match( System::Func error, System::Func resultBlock @@ -101,6 +172,16 @@ public static implicit operator BetaCodeExecutionToolResultBlockContent( BetaCodeExecutionResultBlock value ) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -109,6 +190,17 @@ public void Validate() "Data did not match any variant of BetaCodeExecutionToolResultBlockContent" ); } + this.Switch((error) => error.Validate(), (resultBlock) => resultBlock.Validate()); + } + + public virtual bool Equals(BetaCodeExecutionToolResultBlockContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlockParam.cs index 5a70afc5..296227e5 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -21,74 +20,24 @@ public required BetaCodeExecutionToolResultBlockParamContent Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new ArgumentOutOfRangeException("tool_use_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -98,23 +47,15 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -136,6 +77,11 @@ public BetaCodeExecutionToolResultBlockParam() this.Type = JsonSerializer.Deserialize("\"code_execution_tool_result\""); } + public BetaCodeExecutionToolResultBlockParam( + BetaCodeExecutionToolResultBlockParam betaCodeExecutionToolResultBlockParam + ) + : base(betaCodeExecutionToolResultBlockParam) { } + public BetaCodeExecutionToolResultBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -151,6 +97,7 @@ public BetaCodeExecutionToolResultBlockParam(IReadOnlyDictionary public static BetaCodeExecutionToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -161,6 +108,7 @@ IReadOnlyDictionary rawData class BetaCodeExecutionToolResultBlockParamFromRaw : IFromRaw { + /// public BetaCodeExecutionToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCodeExecutionToolResultBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlockParamContent.cs b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlockParamContent.cs index 678d86c8..b3edaf62 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlockParamContent.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultBlockParamContent.cs @@ -46,6 +46,21 @@ public BetaCodeExecutionToolResultBlockParamContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickErrorParam(out var value)) { + /// // `value` is of type `BetaCodeExecutionToolResultErrorParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickErrorParam( [NotNullWhen(true)] out BetaCodeExecutionToolResultErrorParam? value ) @@ -54,6 +69,21 @@ public bool TryPickErrorParam( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickResultBlockParam(out var value)) { + /// // `value` is of type `BetaCodeExecutionResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickResultBlockParam( [NotNullWhen(true)] out BetaCodeExecutionResultBlockParam? value ) @@ -62,6 +92,26 @@ public bool TryPickResultBlockParam( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaCodeExecutionToolResultErrorParam value) => {...}, + /// (BetaCodeExecutionResultBlockParam value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action errorParam, System::Action resultBlockParam @@ -82,6 +132,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaCodeExecutionToolResultErrorParam value) => {...}, + /// (BetaCodeExecutionResultBlockParam value) => {...} + /// ); + /// + /// + /// public T Match( System::Func errorParam, System::Func resultBlockParam @@ -105,6 +176,16 @@ public static implicit operator BetaCodeExecutionToolResultBlockParamContent( BetaCodeExecutionResultBlockParam value ) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -113,6 +194,20 @@ public void Validate() "Data did not match any variant of BetaCodeExecutionToolResultBlockParamContent" ); } + this.Switch( + (errorParam) => errorParam.Validate(), + (resultBlockParam) => resultBlockParam.Validate() + ); + } + + public virtual bool Equals(BetaCodeExecutionToolResultBlockParamContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultError.cs b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultError.cs index f0c8b002..27703538 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultError.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -21,46 +20,21 @@ public required ApiEnum ErrorCode { get { - if (!this._rawData.TryGetValue("error_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error_code' cannot be null", - new ArgumentOutOfRangeException("error_code", "Missing required argument") - ); - - return JsonSerializer.Deserialize< - ApiEnum - >(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["error_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "error_code" ); } + init { ModelBase.Set(this._rawData, "error_code", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.ErrorCode.Validate(); @@ -80,6 +54,11 @@ public BetaCodeExecutionToolResultError() this.Type = JsonSerializer.Deserialize("\"code_execution_tool_result_error\""); } + public BetaCodeExecutionToolResultError( + BetaCodeExecutionToolResultError betaCodeExecutionToolResultError + ) + : base(betaCodeExecutionToolResultError) { } + public BetaCodeExecutionToolResultError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -95,6 +74,7 @@ public BetaCodeExecutionToolResultError(IReadOnlyDictionary } #pragma warning restore CS8618 + /// public static BetaCodeExecutionToolResultError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -114,6 +94,7 @@ ApiEnum errorCode class BetaCodeExecutionToolResultErrorFromRaw : IFromRaw { + /// public BetaCodeExecutionToolResultError FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCodeExecutionToolResultError.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultErrorParam.cs b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultErrorParam.cs index 12d0d8fd..a2d776a3 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultErrorParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCodeExecutionToolResultErrorParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -21,46 +20,21 @@ public required ApiEnum ErrorCode { get { - if (!this._rawData.TryGetValue("error_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error_code' cannot be null", - new ArgumentOutOfRangeException("error_code", "Missing required argument") - ); - - return JsonSerializer.Deserialize< - ApiEnum - >(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["error_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "error_code" ); } + init { ModelBase.Set(this._rawData, "error_code", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.ErrorCode.Validate(); @@ -80,6 +54,11 @@ public BetaCodeExecutionToolResultErrorParam() this.Type = JsonSerializer.Deserialize("\"code_execution_tool_result_error\""); } + public BetaCodeExecutionToolResultErrorParam( + BetaCodeExecutionToolResultErrorParam betaCodeExecutionToolResultErrorParam + ) + : base(betaCodeExecutionToolResultErrorParam) { } + public BetaCodeExecutionToolResultErrorParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -95,6 +74,7 @@ public BetaCodeExecutionToolResultErrorParam(IReadOnlyDictionary public static BetaCodeExecutionToolResultErrorParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -114,6 +94,7 @@ ApiEnum errorCode class BetaCodeExecutionToolResultErrorParamFromRaw : IFromRaw { + /// public BetaCodeExecutionToolResultErrorParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCodeExecutionToolResultErrorParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaContainer.cs b/src/Anthropic/Models/Beta/Messages/BetaContainer.cs index e23ebfc1..4f0b329c 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaContainer.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaContainer.cs @@ -5,7 +5,6 @@ using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Messages; @@ -20,27 +19,8 @@ public sealed record class BetaContainer : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -48,23 +28,8 @@ public required string ID /// public required DateTimeOffset ExpiresAt { - get - { - if (!this._rawData.TryGetValue("expires_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'expires_at' cannot be null", - new ArgumentOutOfRangeException("expires_at", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["expires_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "expires_at"); } + init { ModelBase.Set(this._rawData, "expires_at", value); } } /// @@ -72,25 +37,11 @@ public required DateTimeOffset ExpiresAt /// public required IReadOnlyList? Skills { - get - { - if (!this._rawData.TryGetValue("skills", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["skills"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "skills"); } + init { ModelBase.Set(this._rawData, "skills", value); } } + /// public override void Validate() { _ = this.ID; @@ -103,6 +54,9 @@ public override void Validate() public BetaContainer() { } + public BetaContainer(BetaContainer betaContainer) + : base(betaContainer) { } + public BetaContainer(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -116,6 +70,7 @@ public BetaContainer(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaContainer FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -124,6 +79,7 @@ public static BetaContainer FromRawUnchecked(IReadOnlyDictionary { + /// public BetaContainer FromRawUnchecked(IReadOnlyDictionary rawData) => BetaContainer.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaContainerParams.cs b/src/Anthropic/Models/Beta/Messages/BetaContainerParams.cs index 985da991..5999c3ff 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaContainerParams.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaContainerParams.cs @@ -18,20 +18,8 @@ public sealed record class BetaContainerParams : ModelBase /// public string? ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -39,25 +27,11 @@ public string? ID /// public IReadOnlyList? Skills { - get - { - if (!this._rawData.TryGetValue("skills", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["skills"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "skills"); } + init { ModelBase.Set(this._rawData, "skills", value); } } + /// public override void Validate() { _ = this.ID; @@ -69,6 +43,9 @@ public override void Validate() public BetaContainerParams() { } + public BetaContainerParams(BetaContainerParams betaContainerParams) + : base(betaContainerParams) { } + public BetaContainerParams(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -82,6 +59,7 @@ public BetaContainerParams(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaContainerParams FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -92,6 +70,7 @@ IReadOnlyDictionary rawData class BetaContainerParamsFromRaw : IFromRaw { + /// public BetaContainerParams FromRawUnchecked(IReadOnlyDictionary rawData) => BetaContainerParams.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaContainerUploadBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaContainerUploadBlock.cs index ba9b82ed..148c4656 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaContainerUploadBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaContainerUploadBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -17,50 +16,17 @@ public sealed record class BetaContainerUploadBlock : ModelBase { public required string FileID { - get - { - if (!this._rawData.TryGetValue("file_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentOutOfRangeException("file_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentNullException("file_id") - ); - } - init - { - this._rawData["file_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "file_id"); } + init { ModelBase.Set(this._rawData, "file_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.FileID; @@ -80,6 +46,9 @@ public BetaContainerUploadBlock() this.Type = JsonSerializer.Deserialize("\"container_upload\""); } + public BetaContainerUploadBlock(BetaContainerUploadBlock betaContainerUploadBlock) + : base(betaContainerUploadBlock) { } + public BetaContainerUploadBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -95,6 +64,7 @@ public BetaContainerUploadBlock(IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaContainerUploadBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -112,6 +82,7 @@ public BetaContainerUploadBlock(string fileID) class BetaContainerUploadBlockFromRaw : IFromRaw { + /// public BetaContainerUploadBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaContainerUploadBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaContainerUploadBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaContainerUploadBlockParam.cs index 036970fc..842653aa 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaContainerUploadBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaContainerUploadBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -20,48 +19,14 @@ public sealed record class BetaContainerUploadBlockParam : ModelBase { public required string FileID { - get - { - if (!this._rawData.TryGetValue("file_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentOutOfRangeException("file_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentNullException("file_id") - ); - } - init - { - this._rawData["file_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "file_id"); } + init { ModelBase.Set(this._rawData, "file_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -71,23 +36,15 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { _ = this.FileID; @@ -108,6 +65,11 @@ public BetaContainerUploadBlockParam() this.Type = JsonSerializer.Deserialize("\"container_upload\""); } + public BetaContainerUploadBlockParam( + BetaContainerUploadBlockParam betaContainerUploadBlockParam + ) + : base(betaContainerUploadBlockParam) { } + public BetaContainerUploadBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -123,6 +85,7 @@ public BetaContainerUploadBlockParam(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaContainerUploadBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -140,6 +103,7 @@ public BetaContainerUploadBlockParam(string fileID) class BetaContainerUploadBlockParamFromRaw : IFromRaw { + /// public BetaContainerUploadBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaContainerUploadBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaContentBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaContentBlock.cs index 5a5d9dd4..0f902aca 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaContentBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaContentBlock.cs @@ -182,36 +182,126 @@ public BetaContentBlock(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickText(out var value)) { + /// // `value` is of type `BetaTextBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickText([NotNullWhen(true)] out BetaTextBlock? value) { value = this.Value as BetaTextBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickThinking(out var value)) { + /// // `value` is of type `BetaThinkingBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickThinking([NotNullWhen(true)] out BetaThinkingBlock? value) { value = this.Value as BetaThinkingBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickRedactedThinking(out var value)) { + /// // `value` is of type `BetaRedactedThinkingBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickRedactedThinking([NotNullWhen(true)] out BetaRedactedThinkingBlock? value) { value = this.Value as BetaRedactedThinkingBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickToolUse(out var value)) { + /// // `value` is of type `BetaToolUseBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickToolUse([NotNullWhen(true)] out BetaToolUseBlock? value) { value = this.Value as BetaToolUseBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickServerToolUse(out var value)) { + /// // `value` is of type `BetaServerToolUseBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickServerToolUse([NotNullWhen(true)] out BetaServerToolUseBlock? value) { value = this.Value as BetaServerToolUseBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickWebSearchToolResult(out var value)) { + /// // `value` is of type `BetaWebSearchToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickWebSearchToolResult( [NotNullWhen(true)] out BetaWebSearchToolResultBlock? value ) @@ -220,6 +310,21 @@ public bool TryPickWebSearchToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickWebFetchToolResult(out var value)) { + /// // `value` is of type `BetaWebFetchToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickWebFetchToolResult( [NotNullWhen(true)] out BetaWebFetchToolResultBlock? value ) @@ -228,6 +333,21 @@ public bool TryPickWebFetchToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCodeExecutionToolResult(out var value)) { + /// // `value` is of type `BetaCodeExecutionToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCodeExecutionToolResult( [NotNullWhen(true)] out BetaCodeExecutionToolResultBlock? value ) @@ -236,6 +356,21 @@ public bool TryPickCodeExecutionToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBashCodeExecutionToolResult(out var value)) { + /// // `value` is of type `BetaBashCodeExecutionToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBashCodeExecutionToolResult( [NotNullWhen(true)] out BetaBashCodeExecutionToolResultBlock? value ) @@ -244,6 +379,21 @@ public bool TryPickBashCodeExecutionToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTextEditorCodeExecutionToolResult(out var value)) { + /// // `value` is of type `BetaTextEditorCodeExecutionToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTextEditorCodeExecutionToolResult( [NotNullWhen(true)] out BetaTextEditorCodeExecutionToolResultBlock? value ) @@ -252,6 +402,21 @@ public bool TryPickTextEditorCodeExecutionToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickToolSearchToolResult(out var value)) { + /// // `value` is of type `BetaToolSearchToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickToolSearchToolResult( [NotNullWhen(true)] out BetaToolSearchToolResultBlock? value ) @@ -260,24 +425,101 @@ public bool TryPickToolSearchToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickMCPToolUse(out var value)) { + /// // `value` is of type `BetaMCPToolUseBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickMCPToolUse([NotNullWhen(true)] out BetaMCPToolUseBlock? value) { value = this.Value as BetaMCPToolUseBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickMCPToolResult(out var value)) { + /// // `value` is of type `BetaMCPToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickMCPToolResult([NotNullWhen(true)] out BetaMCPToolResultBlock? value) { value = this.Value as BetaMCPToolResultBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickContainerUpload(out var value)) { + /// // `value` is of type `BetaContainerUploadBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickContainerUpload([NotNullWhen(true)] out BetaContainerUploadBlock? value) { value = this.Value as BetaContainerUploadBlock; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaTextBlock value) => {...}, + /// (BetaThinkingBlock value) => {...}, + /// (BetaRedactedThinkingBlock value) => {...}, + /// (BetaToolUseBlock value) => {...}, + /// (BetaServerToolUseBlock value) => {...}, + /// (BetaWebSearchToolResultBlock value) => {...}, + /// (BetaWebFetchToolResultBlock value) => {...}, + /// (BetaCodeExecutionToolResultBlock value) => {...}, + /// (BetaBashCodeExecutionToolResultBlock value) => {...}, + /// (BetaTextEditorCodeExecutionToolResultBlock value) => {...}, + /// (BetaToolSearchToolResultBlock value) => {...}, + /// (BetaMCPToolUseBlock value) => {...}, + /// (BetaMCPToolResultBlock value) => {...}, + /// (BetaContainerUploadBlock value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action text, System::Action thinking, @@ -346,6 +588,39 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaTextBlock value) => {...}, + /// (BetaThinkingBlock value) => {...}, + /// (BetaRedactedThinkingBlock value) => {...}, + /// (BetaToolUseBlock value) => {...}, + /// (BetaServerToolUseBlock value) => {...}, + /// (BetaWebSearchToolResultBlock value) => {...}, + /// (BetaWebFetchToolResultBlock value) => {...}, + /// (BetaCodeExecutionToolResultBlock value) => {...}, + /// (BetaBashCodeExecutionToolResultBlock value) => {...}, + /// (BetaTextEditorCodeExecutionToolResultBlock value) => {...}, + /// (BetaToolSearchToolResultBlock value) => {...}, + /// (BetaMCPToolUseBlock value) => {...}, + /// (BetaMCPToolResultBlock value) => {...}, + /// (BetaContainerUploadBlock value) => {...} + /// ); + /// + /// + /// public T Match( System::Func text, System::Func thinking, @@ -425,6 +700,16 @@ public static implicit operator BetaContentBlock(BetaToolSearchToolResultBlock v public static implicit operator BetaContentBlock(BetaContainerUploadBlock value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -433,6 +718,32 @@ public void Validate() "Data did not match any variant of BetaContentBlock" ); } + this.Switch( + (text) => text.Validate(), + (thinking) => thinking.Validate(), + (redactedThinking) => redactedThinking.Validate(), + (toolUse) => toolUse.Validate(), + (serverToolUse) => serverToolUse.Validate(), + (webSearchToolResult) => webSearchToolResult.Validate(), + (webFetchToolResult) => webFetchToolResult.Validate(), + (codeExecutionToolResult) => codeExecutionToolResult.Validate(), + (bashCodeExecutionToolResult) => bashCodeExecutionToolResult.Validate(), + (textEditorCodeExecutionToolResult) => textEditorCodeExecutionToolResult.Validate(), + (toolSearchToolResult) => toolSearchToolResult.Validate(), + (mcpToolUse) => mcpToolUse.Validate(), + (mcpToolResult) => mcpToolResult.Validate(), + (containerUpload) => containerUpload.Validate() + ); + } + + public virtual bool Equals(BetaContentBlock? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaContentBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaContentBlockParam.cs index 49e634dd..172c9c8d 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaContentBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaContentBlockParam.cs @@ -305,36 +305,126 @@ public BetaContentBlockParam(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickText(out var value)) { + /// // `value` is of type `BetaTextBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickText([NotNullWhen(true)] out BetaTextBlockParam? value) { value = this.Value as BetaTextBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickImage(out var value)) { + /// // `value` is of type `BetaImageBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickImage([NotNullWhen(true)] out BetaImageBlockParam? value) { value = this.Value as BetaImageBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickRequestDocumentBlock(out var value)) { + /// // `value` is of type `BetaRequestDocumentBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickRequestDocumentBlock([NotNullWhen(true)] out BetaRequestDocumentBlock? value) { value = this.Value as BetaRequestDocumentBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickSearchResult(out var value)) { + /// // `value` is of type `BetaSearchResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickSearchResult([NotNullWhen(true)] out BetaSearchResultBlockParam? value) { value = this.Value as BetaSearchResultBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickThinking(out var value)) { + /// // `value` is of type `BetaThinkingBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickThinking([NotNullWhen(true)] out BetaThinkingBlockParam? value) { value = this.Value as BetaThinkingBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickRedactedThinking(out var value)) { + /// // `value` is of type `BetaRedactedThinkingBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickRedactedThinking( [NotNullWhen(true)] out BetaRedactedThinkingBlockParam? value ) @@ -343,24 +433,84 @@ public bool TryPickRedactedThinking( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickToolUse(out var value)) { + /// // `value` is of type `BetaToolUseBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickToolUse([NotNullWhen(true)] out BetaToolUseBlockParam? value) { value = this.Value as BetaToolUseBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickToolResult(out var value)) { + /// // `value` is of type `BetaToolResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickToolResult([NotNullWhen(true)] out BetaToolResultBlockParam? value) { value = this.Value as BetaToolResultBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickServerToolUse(out var value)) { + /// // `value` is of type `BetaServerToolUseBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickServerToolUse([NotNullWhen(true)] out BetaServerToolUseBlockParam? value) { value = this.Value as BetaServerToolUseBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickWebSearchToolResult(out var value)) { + /// // `value` is of type `BetaWebSearchToolResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickWebSearchToolResult( [NotNullWhen(true)] out BetaWebSearchToolResultBlockParam? value ) @@ -369,6 +519,21 @@ public bool TryPickWebSearchToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickWebFetchToolResult(out var value)) { + /// // `value` is of type `BetaWebFetchToolResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickWebFetchToolResult( [NotNullWhen(true)] out BetaWebFetchToolResultBlockParam? value ) @@ -377,6 +542,21 @@ public bool TryPickWebFetchToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCodeExecutionToolResult(out var value)) { + /// // `value` is of type `BetaCodeExecutionToolResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCodeExecutionToolResult( [NotNullWhen(true)] out BetaCodeExecutionToolResultBlockParam? value ) @@ -385,6 +565,21 @@ public bool TryPickCodeExecutionToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBashCodeExecutionToolResult(out var value)) { + /// // `value` is of type `BetaBashCodeExecutionToolResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBashCodeExecutionToolResult( [NotNullWhen(true)] out BetaBashCodeExecutionToolResultBlockParam? value ) @@ -393,6 +588,21 @@ public bool TryPickBashCodeExecutionToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTextEditorCodeExecutionToolResult(out var value)) { + /// // `value` is of type `BetaTextEditorCodeExecutionToolResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTextEditorCodeExecutionToolResult( [NotNullWhen(true)] out BetaTextEditorCodeExecutionToolResultBlockParam? value ) @@ -401,6 +611,21 @@ public bool TryPickTextEditorCodeExecutionToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickToolSearchToolResult(out var value)) { + /// // `value` is of type `BetaToolSearchToolResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickToolSearchToolResult( [NotNullWhen(true)] out BetaToolSearchToolResultBlockParam? value ) @@ -409,12 +634,42 @@ public bool TryPickToolSearchToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickMCPToolUse(out var value)) { + /// // `value` is of type `BetaMCPToolUseBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickMCPToolUse([NotNullWhen(true)] out BetaMCPToolUseBlockParam? value) { value = this.Value as BetaMCPToolUseBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickRequestMCPToolResult(out var value)) { + /// // `value` is of type `BetaRequestMCPToolResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickRequestMCPToolResult( [NotNullWhen(true)] out BetaRequestMCPToolResultBlockParam? value ) @@ -423,12 +678,63 @@ public bool TryPickRequestMCPToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickContainerUpload(out var value)) { + /// // `value` is of type `BetaContainerUploadBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickContainerUpload([NotNullWhen(true)] out BetaContainerUploadBlockParam? value) { value = this.Value as BetaContainerUploadBlockParam; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaTextBlockParam value) => {...}, + /// (BetaImageBlockParam value) => {...}, + /// (BetaRequestDocumentBlock value) => {...}, + /// (BetaSearchResultBlockParam value) => {...}, + /// (BetaThinkingBlockParam value) => {...}, + /// (BetaRedactedThinkingBlockParam value) => {...}, + /// (BetaToolUseBlockParam value) => {...}, + /// (BetaToolResultBlockParam value) => {...}, + /// (BetaServerToolUseBlockParam value) => {...}, + /// (BetaWebSearchToolResultBlockParam value) => {...}, + /// (BetaWebFetchToolResultBlockParam value) => {...}, + /// (BetaCodeExecutionToolResultBlockParam value) => {...}, + /// (BetaBashCodeExecutionToolResultBlockParam value) => {...}, + /// (BetaTextEditorCodeExecutionToolResultBlockParam value) => {...}, + /// (BetaToolSearchToolResultBlockParam value) => {...}, + /// (BetaMCPToolUseBlockParam value) => {...}, + /// (BetaRequestMCPToolResultBlockParam value) => {...}, + /// (BetaContainerUploadBlockParam value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action text, System::Action image, @@ -513,6 +819,43 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaTextBlockParam value) => {...}, + /// (BetaImageBlockParam value) => {...}, + /// (BetaRequestDocumentBlock value) => {...}, + /// (BetaSearchResultBlockParam value) => {...}, + /// (BetaThinkingBlockParam value) => {...}, + /// (BetaRedactedThinkingBlockParam value) => {...}, + /// (BetaToolUseBlockParam value) => {...}, + /// (BetaToolResultBlockParam value) => {...}, + /// (BetaServerToolUseBlockParam value) => {...}, + /// (BetaWebSearchToolResultBlockParam value) => {...}, + /// (BetaWebFetchToolResultBlockParam value) => {...}, + /// (BetaCodeExecutionToolResultBlockParam value) => {...}, + /// (BetaBashCodeExecutionToolResultBlockParam value) => {...}, + /// (BetaTextEditorCodeExecutionToolResultBlockParam value) => {...}, + /// (BetaToolSearchToolResultBlockParam value) => {...}, + /// (BetaMCPToolUseBlockParam value) => {...}, + /// (BetaRequestMCPToolResultBlockParam value) => {...}, + /// (BetaContainerUploadBlockParam value) => {...} + /// ); + /// + /// + /// public T Match( System::Func text, System::Func image, @@ -622,6 +965,16 @@ BetaRequestMCPToolResultBlockParam value public static implicit operator BetaContentBlockParam(BetaContainerUploadBlockParam value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -630,6 +983,36 @@ public void Validate() "Data did not match any variant of BetaContentBlockParam" ); } + this.Switch( + (text) => text.Validate(), + (image) => image.Validate(), + (requestDocumentBlock) => requestDocumentBlock.Validate(), + (searchResult) => searchResult.Validate(), + (thinking) => thinking.Validate(), + (redactedThinking) => redactedThinking.Validate(), + (toolUse) => toolUse.Validate(), + (toolResult) => toolResult.Validate(), + (serverToolUse) => serverToolUse.Validate(), + (webSearchToolResult) => webSearchToolResult.Validate(), + (webFetchToolResult) => webFetchToolResult.Validate(), + (codeExecutionToolResult) => codeExecutionToolResult.Validate(), + (bashCodeExecutionToolResult) => bashCodeExecutionToolResult.Validate(), + (textEditorCodeExecutionToolResult) => textEditorCodeExecutionToolResult.Validate(), + (toolSearchToolResult) => toolSearchToolResult.Validate(), + (mcpToolUse) => mcpToolUse.Validate(), + (requestMCPToolResult) => requestMCPToolResult.Validate(), + (containerUpload) => containerUpload.Validate() + ); + } + + public virtual bool Equals(BetaContentBlockParam? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaContentBlockSource.cs b/src/Anthropic/Models/Beta/Messages/BetaContentBlockSource.cs index 464b6966..958f2a20 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaContentBlockSource.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaContentBlockSource.cs @@ -17,51 +17,21 @@ public required BetaContentBlockSourceContent Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -81,6 +51,9 @@ public BetaContentBlockSource() this.Type = JsonSerializer.Deserialize("\"content\""); } + public BetaContentBlockSource(BetaContentBlockSource betaContentBlockSource) + : base(betaContentBlockSource) { } + public BetaContentBlockSource(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -96,6 +69,7 @@ public BetaContentBlockSource(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaContentBlockSource FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -113,6 +87,7 @@ public BetaContentBlockSource(BetaContentBlockSourceContent content) class BetaContentBlockSourceFromRaw : IFromRaw { + /// public BetaContentBlockSource FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaContentBlockSource.FromRawUnchecked(rawData); @@ -150,12 +125,42 @@ public BetaContentBlockSourceContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaContentBlockSource(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaContentBlockSource( [NotNullWhen(true)] out IReadOnlyList? value ) @@ -164,6 +169,26 @@ public bool TryPickBetaContentBlockSource( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action @string, System::Action< @@ -186,6 +211,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match( System::Func @string, System::Func< @@ -211,6 +257,16 @@ public static implicit operator BetaContentBlockSourceContent( List value ) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -220,6 +276,16 @@ public void Validate() ); } } + + public virtual bool Equals(BetaContentBlockSourceContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } } sealed class BetaContentBlockSourceContentConverter : JsonConverter diff --git a/src/Anthropic/Models/Beta/Messages/BetaContextManagementConfig.cs b/src/Anthropic/Models/Beta/Messages/BetaContextManagementConfig.cs index 4fd5e5ec..d1b40d66 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaContextManagementConfig.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaContextManagementConfig.cs @@ -19,13 +19,7 @@ public sealed record class BetaContextManagementConfig : ModelBase /// public IReadOnlyList? Edits { - get - { - if (!this._rawData.TryGetValue("edits", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass>(this.RawData, "edits"); } init { if (value == null) @@ -33,13 +27,11 @@ public IReadOnlyList? Edits return; } - this._rawData["edits"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "edits", value); } } + /// public override void Validate() { foreach (var item in this.Edits ?? []) @@ -50,6 +42,9 @@ public override void Validate() public BetaContextManagementConfig() { } + public BetaContextManagementConfig(BetaContextManagementConfig betaContextManagementConfig) + : base(betaContextManagementConfig) { } + public BetaContextManagementConfig(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -63,6 +58,7 @@ public BetaContextManagementConfig(IReadOnlyDictionary rawD } #pragma warning restore CS8618 + /// public static BetaContextManagementConfig FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -73,6 +69,7 @@ IReadOnlyDictionary rawData class BetaContextManagementConfigFromRaw : IFromRaw { + /// public BetaContextManagementConfig FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaContextManagementConfig.FromRawUnchecked(rawData); @@ -118,6 +115,21 @@ public Edit(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaClearToolUses20250919(out var value)) { + /// // `value` is of type `BetaClearToolUses20250919Edit` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaClearToolUses20250919( [NotNullWhen(true)] out BetaClearToolUses20250919Edit? value ) @@ -126,6 +138,21 @@ public bool TryPickBetaClearToolUses20250919( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaClearThinking20251015(out var value)) { + /// // `value` is of type `BetaClearThinking20251015Edit` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaClearThinking20251015( [NotNullWhen(true)] out BetaClearThinking20251015Edit? value ) @@ -134,6 +161,26 @@ public bool TryPickBetaClearThinking20251015( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaClearToolUses20250919Edit value) => {...}, + /// (BetaClearThinking20251015Edit value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaClearToolUses20250919, System::Action betaClearThinking20251015 @@ -152,6 +199,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaClearToolUses20250919Edit value) => {...}, + /// (BetaClearThinking20251015Edit value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaClearToolUses20250919, System::Func betaClearThinking20251015 @@ -169,12 +237,36 @@ public T Match( public static implicit operator Edit(BetaClearThinking20251015Edit value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of Edit"); } + this.Switch( + (betaClearToolUses20250919) => betaClearToolUses20250919.Validate(), + (betaClearThinking20251015) => betaClearThinking20251015.Validate() + ); + } + + public virtual bool Equals(Edit? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaContextManagementResponse.cs b/src/Anthropic/Models/Beta/Messages/BetaContextManagementResponse.cs index 703dc8f1..c09d16fa 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaContextManagementResponse.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaContextManagementResponse.cs @@ -19,35 +19,11 @@ public sealed record class BetaContextManagementResponse : ModelBase /// public required IReadOnlyList AppliedEdits { - get - { - if (!this._rawData.TryGetValue("applied_edits", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'applied_edits' cannot be null", - new System::ArgumentOutOfRangeException( - "applied_edits", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'applied_edits' cannot be null", - new System::ArgumentNullException("applied_edits") - ); - } - init - { - this._rawData["applied_edits"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "applied_edits"); } + init { ModelBase.Set(this._rawData, "applied_edits", value); } } + /// public override void Validate() { foreach (var item in this.AppliedEdits) @@ -58,6 +34,11 @@ public override void Validate() public BetaContextManagementResponse() { } + public BetaContextManagementResponse( + BetaContextManagementResponse betaContextManagementResponse + ) + : base(betaContextManagementResponse) { } + public BetaContextManagementResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -71,6 +52,7 @@ public BetaContextManagementResponse(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaContextManagementResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -88,6 +70,7 @@ public BetaContextManagementResponse(List appliedEdits) class BetaContextManagementResponseFromRaw : IFromRaw { + /// public BetaContextManagementResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaContextManagementResponse.FromRawUnchecked(rawData); @@ -144,6 +127,21 @@ public AppliedEdit(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaClearToolUses20250919EditResponse(out var value)) { + /// // `value` is of type `BetaClearToolUses20250919EditResponse` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaClearToolUses20250919EditResponse( [NotNullWhen(true)] out BetaClearToolUses20250919EditResponse? value ) @@ -152,6 +150,21 @@ public bool TryPickBetaClearToolUses20250919EditResponse( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaClearThinking20251015EditResponse(out var value)) { + /// // `value` is of type `BetaClearThinking20251015EditResponse` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaClearThinking20251015EditResponse( [NotNullWhen(true)] out BetaClearThinking20251015EditResponse? value ) @@ -160,6 +173,26 @@ public bool TryPickBetaClearThinking20251015EditResponse( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaClearToolUses20250919EditResponse value) => {...}, + /// (BetaClearThinking20251015EditResponse value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaClearToolUses20250919EditResponse, System::Action betaClearThinking20251015EditResponse @@ -180,6 +213,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaClearToolUses20250919EditResponse value) => {...}, + /// (BetaClearThinking20251015EditResponse value) => {...} + /// ); + /// + /// + /// public T Match( System::Func< BetaClearToolUses20250919EditResponse, @@ -208,6 +262,16 @@ public static implicit operator AppliedEdit(BetaClearToolUses20250919EditRespons public static implicit operator AppliedEdit(BetaClearThinking20251015EditResponse value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -216,6 +280,22 @@ public void Validate() "Data did not match any variant of AppliedEdit" ); } + this.Switch( + (betaClearToolUses20250919EditResponse) => + betaClearToolUses20250919EditResponse.Validate(), + (betaClearThinking20251015EditResponse) => + betaClearThinking20251015EditResponse.Validate() + ); + } + + public virtual bool Equals(AppliedEdit? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaCountTokensContextManagementResponse.cs b/src/Anthropic/Models/Beta/Messages/BetaCountTokensContextManagementResponse.cs index 7906a52f..3e89d27e 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaCountTokensContextManagementResponse.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaCountTokensContextManagementResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Messages; @@ -22,28 +20,11 @@ public sealed record class BetaCountTokensContextManagementResponse : ModelBase /// public required long OriginalInputTokens { - get - { - if (!this._rawData.TryGetValue("original_input_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'original_input_tokens' cannot be null", - new ArgumentOutOfRangeException( - "original_input_tokens", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["original_input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "original_input_tokens"); } + init { ModelBase.Set(this._rawData, "original_input_tokens", value); } } + /// public override void Validate() { _ = this.OriginalInputTokens; @@ -51,6 +32,11 @@ public override void Validate() public BetaCountTokensContextManagementResponse() { } + public BetaCountTokensContextManagementResponse( + BetaCountTokensContextManagementResponse betaCountTokensContextManagementResponse + ) + : base(betaCountTokensContextManagementResponse) { } + public BetaCountTokensContextManagementResponse( IReadOnlyDictionary rawData ) @@ -66,6 +52,7 @@ IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaCountTokensContextManagementResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -84,6 +71,7 @@ public BetaCountTokensContextManagementResponse(long originalInputTokens) class BetaCountTokensContextManagementResponseFromRaw : IFromRaw { + /// public BetaCountTokensContextManagementResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaCountTokensContextManagementResponse.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaDirectCaller.cs b/src/Anthropic/Models/Beta/Messages/BetaDirectCaller.cs index 2c25b00b..601540e5 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaDirectCaller.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaDirectCaller.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -17,25 +16,11 @@ public sealed record class BetaDirectCaller : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { if ( @@ -54,6 +39,9 @@ public BetaDirectCaller() this.Type = JsonSerializer.Deserialize("\"direct\""); } + public BetaDirectCaller(BetaDirectCaller betaDirectCaller) + : base(betaDirectCaller) { } + public BetaDirectCaller(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -69,6 +57,7 @@ public BetaDirectCaller(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaDirectCaller FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -79,6 +68,7 @@ IReadOnlyDictionary rawData class BetaDirectCallerFromRaw : IFromRaw { + /// public BetaDirectCaller FromRawUnchecked(IReadOnlyDictionary rawData) => BetaDirectCaller.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaDocumentBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaDocumentBlock.cs index be9edd97..9c82fc31 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaDocumentBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaDocumentBlock.cs @@ -17,48 +17,14 @@ public sealed record class BetaDocumentBlock : ModelBase /// public required BetaCitationConfig? Citations { - get - { - if (!this._rawData.TryGetValue("citations", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["citations"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "citations"); } + init { ModelBase.Set(this._rawData, "citations", value); } } public required Source Source { - get - { - if (!this._rawData.TryGetValue("source", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'source' cannot be null", - new System::ArgumentOutOfRangeException("source", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'source' cannot be null", - new System::ArgumentNullException("source") - ); - } - init - { - this._rawData["source"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "source"); } + init { ModelBase.Set(this._rawData, "source", value); } } /// @@ -66,43 +32,17 @@ public required Source Source /// public required string? Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Citations?.Validate(); @@ -124,6 +64,9 @@ public BetaDocumentBlock() this.Type = JsonSerializer.Deserialize("\"document\""); } + public BetaDocumentBlock(BetaDocumentBlock betaDocumentBlock) + : base(betaDocumentBlock) { } + public BetaDocumentBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -139,6 +82,7 @@ public BetaDocumentBlock(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaDocumentBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -149,6 +93,7 @@ IReadOnlyDictionary rawData class BetaDocumentBlockFromRaw : IFromRaw { + /// public BetaDocumentBlock FromRawUnchecked(IReadOnlyDictionary rawData) => BetaDocumentBlock.FromRawUnchecked(rawData); } @@ -197,18 +142,68 @@ public Source(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaBase64PDF(out var value)) { + /// // `value` is of type `BetaBase64PDFSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaBase64PDF([NotNullWhen(true)] out BetaBase64PDFSource? value) { value = this.Value as BetaBase64PDFSource; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaPlainText(out var value)) { + /// // `value` is of type `BetaPlainTextSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaPlainText([NotNullWhen(true)] out BetaPlainTextSource? value) { value = this.Value as BetaPlainTextSource; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaBase64PDFSource value) => {...}, + /// (BetaPlainTextSource value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaBase64PDF, System::Action betaPlainText @@ -227,6 +222,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaBase64PDFSource value) => {...}, + /// (BetaPlainTextSource value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaBase64PDF, System::Func betaPlainText @@ -246,12 +262,36 @@ public T Match( public static implicit operator Source(BetaPlainTextSource value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of Source"); } + this.Switch( + (betaBase64PDF) => betaBase64PDF.Validate(), + (betaPlainText) => betaPlainText.Validate() + ); + } + + public virtual bool Equals(Source? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaFileDocumentSource.cs b/src/Anthropic/Models/Beta/Messages/BetaFileDocumentSource.cs index 5e63bbb4..0fc7157b 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaFileDocumentSource.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaFileDocumentSource.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaFileDocumentSource : ModelBase { public required string FileID { - get - { - if (!this._rawData.TryGetValue("file_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentOutOfRangeException("file_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentNullException("file_id") - ); - } - init - { - this._rawData["file_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "file_id"); } + init { ModelBase.Set(this._rawData, "file_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.FileID; @@ -72,6 +38,9 @@ public BetaFileDocumentSource() this.Type = JsonSerializer.Deserialize("\"file\""); } + public BetaFileDocumentSource(BetaFileDocumentSource betaFileDocumentSource) + : base(betaFileDocumentSource) { } + public BetaFileDocumentSource(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -87,6 +56,7 @@ public BetaFileDocumentSource(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaFileDocumentSource FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -104,6 +74,7 @@ public BetaFileDocumentSource(string fileID) class BetaFileDocumentSourceFromRaw : IFromRaw { + /// public BetaFileDocumentSource FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaFileDocumentSource.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaFileImageSource.cs b/src/Anthropic/Models/Beta/Messages/BetaFileImageSource.cs index 8356f087..dcebb558 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaFileImageSource.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaFileImageSource.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaFileImageSource : ModelBase { public required string FileID { - get - { - if (!this._rawData.TryGetValue("file_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentOutOfRangeException("file_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'file_id' cannot be null", - new ArgumentNullException("file_id") - ); - } - init - { - this._rawData["file_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "file_id"); } + init { ModelBase.Set(this._rawData, "file_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.FileID; @@ -72,6 +38,9 @@ public BetaFileImageSource() this.Type = JsonSerializer.Deserialize("\"file\""); } + public BetaFileImageSource(BetaFileImageSource betaFileImageSource) + : base(betaFileImageSource) { } + public BetaFileImageSource(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -87,6 +56,7 @@ public BetaFileImageSource(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaFileImageSource FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -104,6 +74,7 @@ public BetaFileImageSource(string fileID) class BetaFileImageSourceFromRaw : IFromRaw { + /// public BetaFileImageSource FromRawUnchecked(IReadOnlyDictionary rawData) => BetaFileImageSource.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaImageBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaImageBlockParam.cs index f05d1bb0..a570723d 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaImageBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaImageBlockParam.cs @@ -14,51 +14,14 @@ public sealed record class BetaImageBlockParam : ModelBase { public required BetaImageBlockParamSource Source { - get - { - if (!this._rawData.TryGetValue("source", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'source' cannot be null", - new System::ArgumentOutOfRangeException("source", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'source' cannot be null", - new System::ArgumentNullException("source") - ); - } - init - { - this._rawData["source"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "source"); } + init { ModelBase.Set(this._rawData, "source", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -68,23 +31,15 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { this.Source.Validate(); @@ -102,6 +57,9 @@ public BetaImageBlockParam() this.Type = JsonSerializer.Deserialize("\"image\""); } + public BetaImageBlockParam(BetaImageBlockParam betaImageBlockParam) + : base(betaImageBlockParam) { } + public BetaImageBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -117,6 +75,7 @@ public BetaImageBlockParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaImageBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -134,6 +93,7 @@ public BetaImageBlockParam(BetaImageBlockParamSource source) class BetaImageBlockParamFromRaw : IFromRaw { + /// public BetaImageBlockParam FromRawUnchecked(IReadOnlyDictionary rawData) => BetaImageBlockParam.FromRawUnchecked(rawData); } @@ -185,24 +145,90 @@ public BetaImageBlockParamSource(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaBase64Image(out var value)) { + /// // `value` is of type `BetaBase64ImageSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaBase64Image([NotNullWhen(true)] out BetaBase64ImageSource? value) { value = this.Value as BetaBase64ImageSource; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaURLImage(out var value)) { + /// // `value` is of type `BetaURLImageSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaURLImage([NotNullWhen(true)] out BetaURLImageSource? value) { value = this.Value as BetaURLImageSource; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaFileImage(out var value)) { + /// // `value` is of type `BetaFileImageSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaFileImage([NotNullWhen(true)] out BetaFileImageSource? value) { value = this.Value as BetaFileImageSource; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaBase64ImageSource value) => {...}, + /// (BetaURLImageSource value) => {...}, + /// (BetaFileImageSource value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaBase64Image, System::Action betaURLImage, @@ -227,6 +253,28 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaBase64ImageSource value) => {...}, + /// (BetaURLImageSource value) => {...}, + /// (BetaFileImageSource value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaBase64Image, System::Func betaURLImage, @@ -253,6 +301,16 @@ public static implicit operator BetaImageBlockParamSource(BetaURLImageSource val public static implicit operator BetaImageBlockParamSource(BetaFileImageSource value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -261,6 +319,21 @@ public void Validate() "Data did not match any variant of BetaImageBlockParamSource" ); } + this.Switch( + (betaBase64Image) => betaBase64Image.Validate(), + (betaURLImage) => betaURLImage.Validate(), + (betaFileImage) => betaFileImage.Validate() + ); + } + + public virtual bool Equals(BetaImageBlockParamSource? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaInputJSONDelta.cs b/src/Anthropic/Models/Beta/Messages/BetaInputJSONDelta.cs index 5822e037..f00c7acf 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaInputJSONDelta.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaInputJSONDelta.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaInputJSONDelta : ModelBase { public required string PartialJSON { - get - { - if (!this._rawData.TryGetValue("partial_json", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'partial_json' cannot be null", - new ArgumentOutOfRangeException("partial_json", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'partial_json' cannot be null", - new ArgumentNullException("partial_json") - ); - } - init - { - this._rawData["partial_json"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "partial_json"); } + init { ModelBase.Set(this._rawData, "partial_json", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.PartialJSON; @@ -77,6 +43,9 @@ public BetaInputJSONDelta() this.Type = JsonSerializer.Deserialize("\"input_json_delta\""); } + public BetaInputJSONDelta(BetaInputJSONDelta betaInputJSONDelta) + : base(betaInputJSONDelta) { } + public BetaInputJSONDelta(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaInputJSONDelta(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaInputJSONDelta FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public BetaInputJSONDelta(string partialJSON) class BetaInputJSONDeltaFromRaw : IFromRaw { + /// public BetaInputJSONDelta FromRawUnchecked(IReadOnlyDictionary rawData) => BetaInputJSONDelta.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaInputTokensClearAtLeast.cs b/src/Anthropic/Models/Beta/Messages/BetaInputTokensClearAtLeast.cs index 74423aba..45bdcc6a 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaInputTokensClearAtLeast.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaInputTokensClearAtLeast.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,46 +15,17 @@ public sealed record class BetaInputTokensClearAtLeast : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required long Value { - get - { - if (!this._rawData.TryGetValue("value", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'value' cannot be null", - new ArgumentOutOfRangeException("value", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["value"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "value"); } + init { ModelBase.Set(this._rawData, "value", value); } } + /// public override void Validate() { if ( @@ -75,6 +45,9 @@ public BetaInputTokensClearAtLeast() this.Type = JsonSerializer.Deserialize("\"input_tokens\""); } + public BetaInputTokensClearAtLeast(BetaInputTokensClearAtLeast betaInputTokensClearAtLeast) + : base(betaInputTokensClearAtLeast) { } + public BetaInputTokensClearAtLeast(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -90,6 +63,7 @@ public BetaInputTokensClearAtLeast(IReadOnlyDictionary rawD } #pragma warning restore CS8618 + /// public static BetaInputTokensClearAtLeast FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -107,6 +81,7 @@ public BetaInputTokensClearAtLeast(long value) class BetaInputTokensClearAtLeastFromRaw : IFromRaw { + /// public BetaInputTokensClearAtLeast FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaInputTokensClearAtLeast.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaInputTokensTrigger.cs b/src/Anthropic/Models/Beta/Messages/BetaInputTokensTrigger.cs index 917cf151..1776e51c 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaInputTokensTrigger.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaInputTokensTrigger.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,46 +13,17 @@ public sealed record class BetaInputTokensTrigger : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required long Value { - get - { - if (!this._rawData.TryGetValue("value", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'value' cannot be null", - new ArgumentOutOfRangeException("value", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["value"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "value"); } + init { ModelBase.Set(this._rawData, "value", value); } } + /// public override void Validate() { if ( @@ -73,6 +43,9 @@ public BetaInputTokensTrigger() this.Type = JsonSerializer.Deserialize("\"input_tokens\""); } + public BetaInputTokensTrigger(BetaInputTokensTrigger betaInputTokensTrigger) + : base(betaInputTokensTrigger) { } + public BetaInputTokensTrigger(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -88,6 +61,7 @@ public BetaInputTokensTrigger(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaInputTokensTrigger FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -105,6 +79,7 @@ public BetaInputTokensTrigger(long value) class BetaInputTokensTriggerFromRaw : IFromRaw { + /// public BetaInputTokensTrigger FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaInputTokensTrigger.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaJSONOutputFormat.cs b/src/Anthropic/Models/Beta/Messages/BetaJSONOutputFormat.cs index 5b5f9d4e..b6719cec 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaJSONOutputFormat.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaJSONOutputFormat.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,51 +18,21 @@ public required IReadOnlyDictionary Schema { get { - if (!this._rawData.TryGetValue("schema", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'schema' cannot be null", - new ArgumentOutOfRangeException("schema", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'schema' cannot be null", - new ArgumentNullException("schema") - ); - } - init - { - this._rawData["schema"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "schema" ); } + init { ModelBase.Set(this._rawData, "schema", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Schema; @@ -83,6 +52,9 @@ public BetaJSONOutputFormat() this.Type = JsonSerializer.Deserialize("\"json_schema\""); } + public BetaJSONOutputFormat(BetaJSONOutputFormat betaJSONOutputFormat) + : base(betaJSONOutputFormat) { } + public BetaJSONOutputFormat(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -98,6 +70,7 @@ public BetaJSONOutputFormat(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaJSONOutputFormat FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -108,6 +81,7 @@ IReadOnlyDictionary rawData class BetaJSONOutputFormatFromRaw : IFromRaw { + /// public BetaJSONOutputFormat FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaJSONOutputFormat.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaMCPToolConfig.cs b/src/Anthropic/Models/Beta/Messages/BetaMCPToolConfig.cs index d96ab2b0..6edde5f4 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMCPToolConfig.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMCPToolConfig.cs @@ -15,13 +15,7 @@ public sealed record class BetaMCPToolConfig : ModelBase { public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -29,22 +23,13 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } public bool? Enabled { - get - { - if (!this._rawData.TryGetValue("enabled", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "enabled"); } init { if (value == null) @@ -52,13 +37,11 @@ public bool? Enabled return; } - this._rawData["enabled"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "enabled", value); } } + /// public override void Validate() { _ = this.DeferLoading; @@ -67,6 +50,9 @@ public override void Validate() public BetaMCPToolConfig() { } + public BetaMCPToolConfig(BetaMCPToolConfig betaMCPToolConfig) + : base(betaMCPToolConfig) { } + public BetaMCPToolConfig(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -80,6 +66,7 @@ public BetaMCPToolConfig(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaMCPToolConfig FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -90,6 +77,7 @@ IReadOnlyDictionary rawData class BetaMCPToolConfigFromRaw : IFromRaw { + /// public BetaMCPToolConfig FromRawUnchecked(IReadOnlyDictionary rawData) => BetaMCPToolConfig.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaMCPToolDefaultConfig.cs b/src/Anthropic/Models/Beta/Messages/BetaMCPToolDefaultConfig.cs index d8e40af5..18597569 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMCPToolDefaultConfig.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMCPToolDefaultConfig.cs @@ -15,13 +15,7 @@ public sealed record class BetaMCPToolDefaultConfig : ModelBase { public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -29,22 +23,13 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } public bool? Enabled { - get - { - if (!this._rawData.TryGetValue("enabled", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "enabled"); } init { if (value == null) @@ -52,13 +37,11 @@ public bool? Enabled return; } - this._rawData["enabled"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "enabled", value); } } + /// public override void Validate() { _ = this.DeferLoading; @@ -67,6 +50,9 @@ public override void Validate() public BetaMCPToolDefaultConfig() { } + public BetaMCPToolDefaultConfig(BetaMCPToolDefaultConfig betaMCPToolDefaultConfig) + : base(betaMCPToolDefaultConfig) { } + public BetaMCPToolDefaultConfig(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -80,6 +66,7 @@ public BetaMCPToolDefaultConfig(IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaMCPToolDefaultConfig FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -90,6 +77,7 @@ IReadOnlyDictionary rawData class BetaMCPToolDefaultConfigFromRaw : IFromRaw { + /// public BetaMCPToolDefaultConfig FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMCPToolDefaultConfig.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaMCPToolResultBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaMCPToolResultBlock.cs index ff6fc6d1..a77dd5df 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMCPToolResultBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMCPToolResultBlock.cs @@ -17,100 +17,33 @@ public required BetaMCPToolResultBlockContent Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required bool IsError { - get - { - if (!this._rawData.TryGetValue("is_error", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'is_error' cannot be null", - new System::ArgumentOutOfRangeException("is_error", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["is_error"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "is_error"); } + init { ModelBase.Set(this._rawData, "is_error", value); } } public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentOutOfRangeException( - "tool_use_id", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -132,6 +65,9 @@ public BetaMCPToolResultBlock() this.Type = JsonSerializer.Deserialize("\"mcp_tool_result\""); } + public BetaMCPToolResultBlock(BetaMCPToolResultBlock betaMCPToolResultBlock) + : base(betaMCPToolResultBlock) { } + public BetaMCPToolResultBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -147,6 +83,7 @@ public BetaMCPToolResultBlock(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaMCPToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -157,6 +94,7 @@ IReadOnlyDictionary rawData class BetaMCPToolResultBlockFromRaw : IFromRaw { + /// public BetaMCPToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMCPToolResultBlock.FromRawUnchecked(rawData); @@ -194,12 +132,42 @@ public BetaMCPToolResultBlockContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaMCPToolResultBlock(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaMCPToolResultBlock( [NotNullWhen(true)] out IReadOnlyList? value ) @@ -208,6 +176,26 @@ public bool TryPickBetaMCPToolResultBlock( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action @string, System::Action> betaMCPToolResultBlockContent @@ -228,6 +216,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match( System::Func @string, System::Func, T> betaMCPToolResultBlockContent @@ -248,6 +257,16 @@ public T Match( public static implicit operator BetaMCPToolResultBlockContent(List value) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -257,6 +276,16 @@ public void Validate() ); } } + + public virtual bool Equals(BetaMCPToolResultBlockContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } } sealed class BetaMCPToolResultBlockContentConverter : JsonConverter diff --git a/src/Anthropic/Models/Beta/Messages/BetaMCPToolUseBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaMCPToolUseBlock.cs index 00addfa3..d9528970 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMCPToolUseBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMCPToolUseBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,55 +13,20 @@ public sealed record class BetaMCPToolUseBlock : ModelBase { public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } public required IReadOnlyDictionary Input { get { - if (!this._rawData.TryGetValue("input", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input' cannot be null", - new ArgumentOutOfRangeException("input", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'input' cannot be null", - new ArgumentNullException("input") - ); - } - init - { - this._rawData["input"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "input" ); } + init { ModelBase.Set(this._rawData, "input", value); } } /// @@ -70,27 +34,8 @@ public required IReadOnlyDictionary Input /// public required string Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentNullException("name") - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } /// @@ -98,50 +43,17 @@ public required string Name /// public required string ServerName { - get - { - if (!this._rawData.TryGetValue("server_name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'server_name' cannot be null", - new ArgumentOutOfRangeException("server_name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'server_name' cannot be null", - new ArgumentNullException("server_name") - ); - } - init - { - this._rawData["server_name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "server_name"); } + init { ModelBase.Set(this._rawData, "server_name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ID; @@ -164,6 +76,9 @@ public BetaMCPToolUseBlock() this.Type = JsonSerializer.Deserialize("\"mcp_tool_use\""); } + public BetaMCPToolUseBlock(BetaMCPToolUseBlock betaMCPToolUseBlock) + : base(betaMCPToolUseBlock) { } + public BetaMCPToolUseBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -179,6 +94,7 @@ public BetaMCPToolUseBlock(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaMCPToolUseBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -189,6 +105,7 @@ IReadOnlyDictionary rawData class BetaMCPToolUseBlockFromRaw : IFromRaw { + /// public BetaMCPToolUseBlock FromRawUnchecked(IReadOnlyDictionary rawData) => BetaMCPToolUseBlock.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaMCPToolUseBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaMCPToolUseBlockParam.cs index df061a7c..284e43a6 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMCPToolUseBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMCPToolUseBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,80 +13,26 @@ public sealed record class BetaMCPToolUseBlockParam : ModelBase { public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } public required IReadOnlyDictionary Input { get { - if (!this._rawData.TryGetValue("input", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input' cannot be null", - new ArgumentOutOfRangeException("input", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'input' cannot be null", - new ArgumentNullException("input") - ); - } - init - { - this._rawData["input"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "input" ); } + init { ModelBase.Set(this._rawData, "input", value); } } public required string Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentNullException("name") - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } /// @@ -95,48 +40,14 @@ public required string Name /// public required string ServerName { - get - { - if (!this._rawData.TryGetValue("server_name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'server_name' cannot be null", - new ArgumentOutOfRangeException("server_name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'server_name' cannot be null", - new ArgumentNullException("server_name") - ); - } - init - { - this._rawData["server_name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "server_name"); } + init { ModelBase.Set(this._rawData, "server_name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -146,23 +57,15 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { _ = this.ID; @@ -186,6 +89,9 @@ public BetaMCPToolUseBlockParam() this.Type = JsonSerializer.Deserialize("\"mcp_tool_use\""); } + public BetaMCPToolUseBlockParam(BetaMCPToolUseBlockParam betaMCPToolUseBlockParam) + : base(betaMCPToolUseBlockParam) { } + public BetaMCPToolUseBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -201,6 +107,7 @@ public BetaMCPToolUseBlockParam(IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaMCPToolUseBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -211,6 +118,7 @@ IReadOnlyDictionary rawData class BetaMCPToolUseBlockParamFromRaw : IFromRaw { + /// public BetaMCPToolUseBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMCPToolUseBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaMCPToolset.cs b/src/Anthropic/Models/Beta/Messages/BetaMCPToolset.cs index 6a1fe9b9..8ce7b6c5 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMCPToolset.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMCPToolset.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -23,48 +22,14 @@ public sealed record class BetaMCPToolset : ModelBase /// public required string MCPServerName { - get - { - if (!this._rawData.TryGetValue("mcp_server_name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'mcp_server_name' cannot be null", - new ArgumentOutOfRangeException("mcp_server_name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'mcp_server_name' cannot be null", - new ArgumentNullException("mcp_server_name") - ); - } - init - { - this._rawData["mcp_server_name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "mcp_server_name"); } + init { ModelBase.Set(this._rawData, "mcp_server_name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -74,21 +39,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -98,21 +54,12 @@ public IReadOnlyDictionary? Configs { get { - if (!this._rawData.TryGetValue("configs", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["configs"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawData, + "configs" ); } + init { ModelBase.Set(this._rawData, "configs", value); } } /// @@ -122,12 +69,9 @@ public BetaMCPToolDefaultConfig? DefaultConfig { get { - if (!this._rawData.TryGetValue("default_config", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "default_config" ); } init @@ -137,13 +81,11 @@ public BetaMCPToolDefaultConfig? DefaultConfig return; } - this._rawData["default_config"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "default_config", value); } } + /// public override void Validate() { _ = this.MCPServerName; @@ -172,6 +114,9 @@ public BetaMCPToolset() this.Type = JsonSerializer.Deserialize("\"mcp_toolset\""); } + public BetaMCPToolset(BetaMCPToolset betaMCPToolset) + : base(betaMCPToolset) { } + public BetaMCPToolset(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -187,6 +132,7 @@ public BetaMCPToolset(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaMCPToolset FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -202,6 +148,7 @@ public BetaMCPToolset(string mcpServerName) class BetaMCPToolsetFromRaw : IFromRaw { + /// public BetaMCPToolset FromRawUnchecked(IReadOnlyDictionary rawData) => BetaMCPToolset.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818.cs b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818.cs index 7d9a991b..d9d3df10 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818.cs @@ -19,57 +19,23 @@ public sealed record class BetaMemoryTool20250818 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList>? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + List> + >(this.RawData, "allowed_callers"); } init { @@ -78,10 +44,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -92,21 +55,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -115,13 +69,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -129,10 +77,7 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } @@ -140,12 +85,9 @@ public IReadOnlyList>? InputExamples { get { - if (!this._rawData.TryGetValue("input_examples", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawData, + "input_examples" ); } init @@ -155,22 +97,13 @@ public IReadOnlyList>? InputExamples return; } - this._rawData["input_examples"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "input_examples", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -178,13 +111,11 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } + /// public override void Validate() { if ( @@ -221,6 +152,9 @@ public BetaMemoryTool20250818() this.Type = JsonSerializer.Deserialize("\"memory_20250818\""); } + public BetaMemoryTool20250818(BetaMemoryTool20250818 betaMemoryTool20250818) + : base(betaMemoryTool20250818) { } + public BetaMemoryTool20250818(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -237,6 +171,7 @@ public BetaMemoryTool20250818(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaMemoryTool20250818 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -247,21 +182,23 @@ IReadOnlyDictionary rawData class BetaMemoryTool20250818FromRaw : IFromRaw { + /// public BetaMemoryTool20250818 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMemoryTool20250818.FromRawUnchecked(rawData); } -[JsonConverter(typeof(AllowedCaller1Converter))] -public enum AllowedCaller1 +[JsonConverter(typeof(BetaMemoryTool20250818AllowedCallerConverter))] +public enum BetaMemoryTool20250818AllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCaller1Converter : JsonConverter +sealed class BetaMemoryTool20250818AllowedCallerConverter + : JsonConverter { - public override AllowedCaller1 Read( + public override BetaMemoryTool20250818AllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -269,15 +206,15 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCaller1.Direct, - "code_execution_20250825" => AllowedCaller1.CodeExecution20250825, - _ => (AllowedCaller1)(-1), + "direct" => BetaMemoryTool20250818AllowedCaller.Direct, + "code_execution_20250825" => BetaMemoryTool20250818AllowedCaller.CodeExecution20250825, + _ => (BetaMemoryTool20250818AllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCaller1 value, + BetaMemoryTool20250818AllowedCaller value, JsonSerializerOptions options ) { @@ -285,8 +222,9 @@ JsonSerializerOptions options writer, value switch { - AllowedCaller1.Direct => "direct", - AllowedCaller1.CodeExecution20250825 => "code_execution_20250825", + BetaMemoryTool20250818AllowedCaller.Direct => "direct", + BetaMemoryTool20250818AllowedCaller.CodeExecution20250825 => + "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), diff --git a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818Command.cs b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818Command.cs index 5e3df66c..02f9c9af 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818Command.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818Command.cs @@ -107,6 +107,21 @@ public BetaMemoryTool20250818Command(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTool20250818View(out var value)) { + /// // `value` is of type `BetaMemoryTool20250818ViewCommand` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTool20250818View( [NotNullWhen(true)] out BetaMemoryTool20250818ViewCommand? value ) @@ -115,6 +130,21 @@ public bool TryPickTool20250818View( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTool20250818Create(out var value)) { + /// // `value` is of type `BetaMemoryTool20250818CreateCommand` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTool20250818Create( [NotNullWhen(true)] out BetaMemoryTool20250818CreateCommand? value ) @@ -123,6 +153,21 @@ public bool TryPickTool20250818Create( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTool20250818StrReplace(out var value)) { + /// // `value` is of type `BetaMemoryTool20250818StrReplaceCommand` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTool20250818StrReplace( [NotNullWhen(true)] out BetaMemoryTool20250818StrReplaceCommand? value ) @@ -131,6 +176,21 @@ public bool TryPickTool20250818StrReplace( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTool20250818Insert(out var value)) { + /// // `value` is of type `BetaMemoryTool20250818InsertCommand` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTool20250818Insert( [NotNullWhen(true)] out BetaMemoryTool20250818InsertCommand? value ) @@ -139,6 +199,21 @@ public bool TryPickTool20250818Insert( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTool20250818Delete(out var value)) { + /// // `value` is of type `BetaMemoryTool20250818DeleteCommand` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTool20250818Delete( [NotNullWhen(true)] out BetaMemoryTool20250818DeleteCommand? value ) @@ -147,6 +222,21 @@ public bool TryPickTool20250818Delete( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTool20250818Rename(out var value)) { + /// // `value` is of type `BetaMemoryTool20250818RenameCommand` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTool20250818Rename( [NotNullWhen(true)] out BetaMemoryTool20250818RenameCommand? value ) @@ -155,6 +245,30 @@ public bool TryPickTool20250818Rename( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaMemoryTool20250818ViewCommand value) => {...}, + /// (BetaMemoryTool20250818CreateCommand value) => {...}, + /// (BetaMemoryTool20250818StrReplaceCommand value) => {...}, + /// (BetaMemoryTool20250818InsertCommand value) => {...}, + /// (BetaMemoryTool20250818DeleteCommand value) => {...}, + /// (BetaMemoryTool20250818RenameCommand value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action tool20250818View, System::Action tool20250818Create, @@ -191,6 +305,31 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaMemoryTool20250818ViewCommand value) => {...}, + /// (BetaMemoryTool20250818CreateCommand value) => {...}, + /// (BetaMemoryTool20250818StrReplaceCommand value) => {...}, + /// (BetaMemoryTool20250818InsertCommand value) => {...}, + /// (BetaMemoryTool20250818DeleteCommand value) => {...}, + /// (BetaMemoryTool20250818RenameCommand value) => {...} + /// ); + /// + /// + /// public T Match( System::Func tool20250818View, System::Func tool20250818Create, @@ -238,6 +377,16 @@ public static implicit operator BetaMemoryTool20250818Command( BetaMemoryTool20250818RenameCommand value ) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -246,6 +395,24 @@ public void Validate() "Data did not match any variant of BetaMemoryTool20250818Command" ); } + this.Switch( + (tool20250818View) => tool20250818View.Validate(), + (tool20250818Create) => tool20250818Create.Validate(), + (tool20250818StrReplace) => tool20250818StrReplace.Validate(), + (tool20250818Insert) => tool20250818Insert.Validate(), + (tool20250818Delete) => tool20250818Delete.Validate(), + (tool20250818Rename) => tool20250818Rename.Validate() + ); + } + + public virtual bool Equals(BetaMemoryTool20250818Command? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818CreateCommand.cs b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818CreateCommand.cs index 577cf91f..495c1fe1 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818CreateCommand.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818CreateCommand.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -22,23 +21,8 @@ public sealed record class BetaMemoryTool20250818CreateCommand : ModelBase /// public JsonElement Command { - get - { - if (!this._rawData.TryGetValue("command", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'command' cannot be null", - new ArgumentOutOfRangeException("command", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["command"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "command"); } + init { ModelBase.Set(this._rawData, "command", value); } } /// @@ -46,27 +30,8 @@ public JsonElement Command /// public required string FileText { - get - { - if (!this._rawData.TryGetValue("file_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'file_text' cannot be null", - new ArgumentOutOfRangeException("file_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'file_text' cannot be null", - new ArgumentNullException("file_text") - ); - } - init - { - this._rawData["file_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "file_text"); } + init { ModelBase.Set(this._rawData, "file_text", value); } } /// @@ -74,29 +39,11 @@ public required string FileText /// public required string Path { - get - { - if (!this._rawData.TryGetValue("path", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'path' cannot be null", - new ArgumentOutOfRangeException("path", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'path' cannot be null", - new ArgumentNullException("path") - ); - } - init - { - this._rawData["path"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "path"); } + init { ModelBase.Set(this._rawData, "path", value); } } + /// public override void Validate() { if ( @@ -117,6 +64,11 @@ public BetaMemoryTool20250818CreateCommand() this.Command = JsonSerializer.Deserialize("\"create\""); } + public BetaMemoryTool20250818CreateCommand( + BetaMemoryTool20250818CreateCommand betaMemoryTool20250818CreateCommand + ) + : base(betaMemoryTool20250818CreateCommand) { } + public BetaMemoryTool20250818CreateCommand(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -132,6 +84,7 @@ public BetaMemoryTool20250818CreateCommand(IReadOnlyDictionary public static BetaMemoryTool20250818CreateCommand FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -142,6 +95,7 @@ IReadOnlyDictionary rawData class BetaMemoryTool20250818CreateCommandFromRaw : IFromRaw { + /// public BetaMemoryTool20250818CreateCommand FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMemoryTool20250818CreateCommand.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818DeleteCommand.cs b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818DeleteCommand.cs index ea06792b..8c062c25 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818DeleteCommand.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818DeleteCommand.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -22,23 +21,8 @@ public sealed record class BetaMemoryTool20250818DeleteCommand : ModelBase /// public JsonElement Command { - get - { - if (!this._rawData.TryGetValue("command", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'command' cannot be null", - new ArgumentOutOfRangeException("command", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["command"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "command"); } + init { ModelBase.Set(this._rawData, "command", value); } } /// @@ -46,29 +30,11 @@ public JsonElement Command /// public required string Path { - get - { - if (!this._rawData.TryGetValue("path", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'path' cannot be null", - new ArgumentOutOfRangeException("path", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'path' cannot be null", - new ArgumentNullException("path") - ); - } - init - { - this._rawData["path"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "path"); } + init { ModelBase.Set(this._rawData, "path", value); } } + /// public override void Validate() { if ( @@ -88,6 +54,11 @@ public BetaMemoryTool20250818DeleteCommand() this.Command = JsonSerializer.Deserialize("\"delete\""); } + public BetaMemoryTool20250818DeleteCommand( + BetaMemoryTool20250818DeleteCommand betaMemoryTool20250818DeleteCommand + ) + : base(betaMemoryTool20250818DeleteCommand) { } + public BetaMemoryTool20250818DeleteCommand(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -103,6 +74,7 @@ public BetaMemoryTool20250818DeleteCommand(IReadOnlyDictionary public static BetaMemoryTool20250818DeleteCommand FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -120,6 +92,7 @@ public BetaMemoryTool20250818DeleteCommand(string path) class BetaMemoryTool20250818DeleteCommandFromRaw : IFromRaw { + /// public BetaMemoryTool20250818DeleteCommand FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMemoryTool20250818DeleteCommand.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818InsertCommand.cs b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818InsertCommand.cs index 6eb2a50a..77adbfb7 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818InsertCommand.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818InsertCommand.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -22,23 +21,8 @@ public sealed record class BetaMemoryTool20250818InsertCommand : ModelBase /// public JsonElement Command { - get - { - if (!this._rawData.TryGetValue("command", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'command' cannot be null", - new ArgumentOutOfRangeException("command", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["command"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "command"); } + init { ModelBase.Set(this._rawData, "command", value); } } /// @@ -46,23 +30,8 @@ public JsonElement Command /// public required long InsertLine { - get - { - if (!this._rawData.TryGetValue("insert_line", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'insert_line' cannot be null", - new ArgumentOutOfRangeException("insert_line", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["insert_line"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "insert_line"); } + init { ModelBase.Set(this._rawData, "insert_line", value); } } /// @@ -70,27 +39,8 @@ public required long InsertLine /// public required string InsertText { - get - { - if (!this._rawData.TryGetValue("insert_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'insert_text' cannot be null", - new ArgumentOutOfRangeException("insert_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'insert_text' cannot be null", - new ArgumentNullException("insert_text") - ); - } - init - { - this._rawData["insert_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "insert_text"); } + init { ModelBase.Set(this._rawData, "insert_text", value); } } /// @@ -98,29 +48,11 @@ public required string InsertText /// public required string Path { - get - { - if (!this._rawData.TryGetValue("path", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'path' cannot be null", - new ArgumentOutOfRangeException("path", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'path' cannot be null", - new ArgumentNullException("path") - ); - } - init - { - this._rawData["path"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "path"); } + init { ModelBase.Set(this._rawData, "path", value); } } + /// public override void Validate() { if ( @@ -142,6 +74,11 @@ public BetaMemoryTool20250818InsertCommand() this.Command = JsonSerializer.Deserialize("\"insert\""); } + public BetaMemoryTool20250818InsertCommand( + BetaMemoryTool20250818InsertCommand betaMemoryTool20250818InsertCommand + ) + : base(betaMemoryTool20250818InsertCommand) { } + public BetaMemoryTool20250818InsertCommand(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -157,6 +94,7 @@ public BetaMemoryTool20250818InsertCommand(IReadOnlyDictionary public static BetaMemoryTool20250818InsertCommand FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -167,6 +105,7 @@ IReadOnlyDictionary rawData class BetaMemoryTool20250818InsertCommandFromRaw : IFromRaw { + /// public BetaMemoryTool20250818InsertCommand FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMemoryTool20250818InsertCommand.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818RenameCommand.cs b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818RenameCommand.cs index cd76ad0a..71d7b51b 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818RenameCommand.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818RenameCommand.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -22,23 +21,8 @@ public sealed record class BetaMemoryTool20250818RenameCommand : ModelBase /// public JsonElement Command { - get - { - if (!this._rawData.TryGetValue("command", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'command' cannot be null", - new ArgumentOutOfRangeException("command", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["command"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "command"); } + init { ModelBase.Set(this._rawData, "command", value); } } /// @@ -46,27 +30,8 @@ public JsonElement Command /// public required string NewPath { - get - { - if (!this._rawData.TryGetValue("new_path", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'new_path' cannot be null", - new ArgumentOutOfRangeException("new_path", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'new_path' cannot be null", - new ArgumentNullException("new_path") - ); - } - init - { - this._rawData["new_path"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "new_path"); } + init { ModelBase.Set(this._rawData, "new_path", value); } } /// @@ -74,29 +39,11 @@ public required string NewPath /// public required string OldPath { - get - { - if (!this._rawData.TryGetValue("old_path", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'old_path' cannot be null", - new ArgumentOutOfRangeException("old_path", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'old_path' cannot be null", - new ArgumentNullException("old_path") - ); - } - init - { - this._rawData["old_path"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "old_path"); } + init { ModelBase.Set(this._rawData, "old_path", value); } } + /// public override void Validate() { if ( @@ -117,6 +64,11 @@ public BetaMemoryTool20250818RenameCommand() this.Command = JsonSerializer.Deserialize("\"rename\""); } + public BetaMemoryTool20250818RenameCommand( + BetaMemoryTool20250818RenameCommand betaMemoryTool20250818RenameCommand + ) + : base(betaMemoryTool20250818RenameCommand) { } + public BetaMemoryTool20250818RenameCommand(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -132,6 +84,7 @@ public BetaMemoryTool20250818RenameCommand(IReadOnlyDictionary public static BetaMemoryTool20250818RenameCommand FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -142,6 +95,7 @@ IReadOnlyDictionary rawData class BetaMemoryTool20250818RenameCommandFromRaw : IFromRaw { + /// public BetaMemoryTool20250818RenameCommand FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMemoryTool20250818RenameCommand.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818StrReplaceCommand.cs b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818StrReplaceCommand.cs index 9f4045d8..150cd39a 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818StrReplaceCommand.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818StrReplaceCommand.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -22,23 +21,8 @@ public sealed record class BetaMemoryTool20250818StrReplaceCommand : ModelBase /// public JsonElement Command { - get - { - if (!this._rawData.TryGetValue("command", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'command' cannot be null", - new ArgumentOutOfRangeException("command", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["command"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "command"); } + init { ModelBase.Set(this._rawData, "command", value); } } /// @@ -46,27 +30,8 @@ public JsonElement Command /// public required string NewStr { - get - { - if (!this._rawData.TryGetValue("new_str", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'new_str' cannot be null", - new ArgumentOutOfRangeException("new_str", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'new_str' cannot be null", - new ArgumentNullException("new_str") - ); - } - init - { - this._rawData["new_str"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "new_str"); } + init { ModelBase.Set(this._rawData, "new_str", value); } } /// @@ -74,27 +39,8 @@ public required string NewStr /// public required string OldStr { - get - { - if (!this._rawData.TryGetValue("old_str", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'old_str' cannot be null", - new ArgumentOutOfRangeException("old_str", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'old_str' cannot be null", - new ArgumentNullException("old_str") - ); - } - init - { - this._rawData["old_str"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "old_str"); } + init { ModelBase.Set(this._rawData, "old_str", value); } } /// @@ -102,29 +48,11 @@ public required string OldStr /// public required string Path { - get - { - if (!this._rawData.TryGetValue("path", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'path' cannot be null", - new ArgumentOutOfRangeException("path", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'path' cannot be null", - new ArgumentNullException("path") - ); - } - init - { - this._rawData["path"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "path"); } + init { ModelBase.Set(this._rawData, "path", value); } } + /// public override void Validate() { if ( @@ -146,6 +74,11 @@ public BetaMemoryTool20250818StrReplaceCommand() this.Command = JsonSerializer.Deserialize("\"str_replace\""); } + public BetaMemoryTool20250818StrReplaceCommand( + BetaMemoryTool20250818StrReplaceCommand betaMemoryTool20250818StrReplaceCommand + ) + : base(betaMemoryTool20250818StrReplaceCommand) { } + public BetaMemoryTool20250818StrReplaceCommand(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -161,6 +94,7 @@ public BetaMemoryTool20250818StrReplaceCommand(IReadOnlyDictionary public static BetaMemoryTool20250818StrReplaceCommand FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -172,6 +106,7 @@ IReadOnlyDictionary rawData class BetaMemoryTool20250818StrReplaceCommandFromRaw : IFromRaw { + /// public BetaMemoryTool20250818StrReplaceCommand FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMemoryTool20250818StrReplaceCommand.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818ViewCommand.cs b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818ViewCommand.cs index 3cbb39db..94b3d47e 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818ViewCommand.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMemoryTool20250818ViewCommand.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -22,23 +21,8 @@ public sealed record class BetaMemoryTool20250818ViewCommand : ModelBase /// public JsonElement Command { - get - { - if (!this._rawData.TryGetValue("command", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'command' cannot be null", - new ArgumentOutOfRangeException("command", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["command"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "command"); } + init { ModelBase.Set(this._rawData, "command", value); } } /// @@ -46,27 +30,8 @@ public JsonElement Command /// public required string Path { - get - { - if (!this._rawData.TryGetValue("path", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'path' cannot be null", - new ArgumentOutOfRangeException("path", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'path' cannot be null", - new ArgumentNullException("path") - ); - } - init - { - this._rawData["path"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "path"); } + init { ModelBase.Set(this._rawData, "path", value); } } /// @@ -74,13 +39,7 @@ public required string Path /// public IReadOnlyList? ViewRange { - get - { - if (!this._rawData.TryGetValue("view_range", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass>(this.RawData, "view_range"); } init { if (value == null) @@ -88,13 +47,11 @@ public IReadOnlyList? ViewRange return; } - this._rawData["view_range"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "view_range", value); } } + /// public override void Validate() { if ( @@ -115,6 +72,11 @@ public BetaMemoryTool20250818ViewCommand() this.Command = JsonSerializer.Deserialize("\"view\""); } + public BetaMemoryTool20250818ViewCommand( + BetaMemoryTool20250818ViewCommand betaMemoryTool20250818ViewCommand + ) + : base(betaMemoryTool20250818ViewCommand) { } + public BetaMemoryTool20250818ViewCommand(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -130,6 +92,7 @@ public BetaMemoryTool20250818ViewCommand(IReadOnlyDictionary public static BetaMemoryTool20250818ViewCommand FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -147,6 +110,7 @@ public BetaMemoryTool20250818ViewCommand(string path) class BetaMemoryTool20250818ViewCommandFromRaw : IFromRaw { + /// public BetaMemoryTool20250818ViewCommand FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMemoryTool20250818ViewCommand.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaMessage.cs b/src/Anthropic/Models/Beta/Messages/BetaMessage.cs index 41e6539e..0883594b 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMessage.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMessage.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -20,27 +19,8 @@ public sealed record class BetaMessage : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -48,20 +28,8 @@ public required string ID /// public required BetaContainer? Container { - get - { - if (!this._rawData.TryGetValue("container", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["container"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "container"); } + init { ModelBase.Set(this._rawData, "container", value); } } /// @@ -88,30 +56,8 @@ public required BetaContainer? Container /// public required IReadOnlyList Content { - get - { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "content"); } + init { ModelBase.Set(this._rawData, "content", value); } } /// @@ -123,21 +69,12 @@ public required BetaContextManagementResponse? ContextManagement { get { - if (!this._rawData.TryGetValue("context_management", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["context_management"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "context_management" ); } + init { ModelBase.Set(this._rawData, "context_management", value); } } /// @@ -146,26 +83,8 @@ public required BetaContextManagementResponse? ContextManagement /// public required ApiEnum Model { - get - { - if (!this._rawData.TryGetValue("model", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'model' cannot be null", - new ArgumentOutOfRangeException("model", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["model"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "model"); } + init { ModelBase.Set(this._rawData, "model", value); } } /// @@ -175,23 +94,8 @@ public required ApiEnum Model /// public JsonElement Role { - get - { - if (!this._rawData.TryGetValue("role", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'role' cannot be null", - new ArgumentOutOfRangeException("role", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["role"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "role"); } + init { ModelBase.Set(this._rawData, "role", value); } } /// @@ -212,21 +116,12 @@ public required ApiEnum? StopReason { get { - if (!this._rawData.TryGetValue("stop_reason", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["stop_reason"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawData, + "stop_reason" ); } + init { ModelBase.Set(this._rawData, "stop_reason", value); } } /// @@ -237,20 +132,8 @@ public required ApiEnum? StopReason /// public required string? StopSequence { - get - { - if (!this._rawData.TryGetValue("stop_sequence", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["stop_sequence"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "stop_sequence"); } + init { ModelBase.Set(this._rawData, "stop_sequence", value); } } /// @@ -260,23 +143,8 @@ public required string? StopSequence /// public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -298,29 +166,11 @@ public JsonElement Type /// public required BetaUsage Usage { - get - { - if (!this._rawData.TryGetValue("usage", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'usage' cannot be null", - new ArgumentOutOfRangeException("usage", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'usage' cannot be null", - new ArgumentNullException("usage") - ); - } - init - { - this._rawData["usage"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "usage"); } + init { ModelBase.Set(this._rawData, "usage", value); } } + /// public override void Validate() { _ = this.ID; @@ -360,6 +210,9 @@ public BetaMessage() this.Type = JsonSerializer.Deserialize("\"message\""); } + public BetaMessage(BetaMessage betaMessage) + : base(betaMessage) { } + public BetaMessage(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -376,6 +229,7 @@ public BetaMessage(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaMessage FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -384,6 +238,7 @@ public static BetaMessage FromRawUnchecked(IReadOnlyDictionary { + /// public BetaMessage FromRawUnchecked(IReadOnlyDictionary rawData) => BetaMessage.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaMessageDeltaUsage.cs b/src/Anthropic/Models/Beta/Messages/BetaMessageDeltaUsage.cs index d1e4db7f..c5e36d09 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMessageDeltaUsage.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMessageDeltaUsage.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Messages; @@ -19,18 +17,9 @@ public required long? CacheCreationInputTokens { get { - if (!this._rawData.TryGetValue("cache_creation_input_tokens", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["cache_creation_input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableStruct(this.RawData, "cache_creation_input_tokens"); } + init { ModelBase.Set(this._rawData, "cache_creation_input_tokens", value); } } /// @@ -38,20 +27,8 @@ public required long? CacheCreationInputTokens /// public required long? CacheReadInputTokens { - get - { - if (!this._rawData.TryGetValue("cache_read_input_tokens", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["cache_read_input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "cache_read_input_tokens"); } + init { ModelBase.Set(this._rawData, "cache_read_input_tokens", value); } } /// @@ -59,20 +36,8 @@ public required long? CacheReadInputTokens /// public required long? InputTokens { - get - { - if (!this._rawData.TryGetValue("input_tokens", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "input_tokens"); } + init { ModelBase.Set(this._rawData, "input_tokens", value); } } /// @@ -80,23 +45,8 @@ public required long? InputTokens /// public required long OutputTokens { - get - { - if (!this._rawData.TryGetValue("output_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'output_tokens' cannot be null", - new ArgumentOutOfRangeException("output_tokens", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["output_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "output_tokens"); } + init { ModelBase.Set(this._rawData, "output_tokens", value); } } /// @@ -106,23 +56,12 @@ public required BetaServerToolUsage? ServerToolUse { get { - if (!this._rawData.TryGetValue("server_tool_use", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["server_tool_use"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "server_tool_use"); } + init { ModelBase.Set(this._rawData, "server_tool_use", value); } } + /// public override void Validate() { _ = this.CacheCreationInputTokens; @@ -134,6 +73,9 @@ public override void Validate() public BetaMessageDeltaUsage() { } + public BetaMessageDeltaUsage(BetaMessageDeltaUsage betaMessageDeltaUsage) + : base(betaMessageDeltaUsage) { } + public BetaMessageDeltaUsage(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -147,6 +89,7 @@ public BetaMessageDeltaUsage(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaMessageDeltaUsage FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -157,6 +100,7 @@ IReadOnlyDictionary rawData class BetaMessageDeltaUsageFromRaw : IFromRaw { + /// public BetaMessageDeltaUsage FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMessageDeltaUsage.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaMessageParam.cs b/src/Anthropic/Models/Beta/Messages/BetaMessageParam.cs index 778bcbfa..0f11f04a 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMessageParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMessageParam.cs @@ -15,56 +15,17 @@ public sealed record class BetaMessageParam : ModelBase { public required BetaMessageParamContent Content { - get - { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "content"); } + init { ModelBase.Set(this._rawData, "content", value); } } public required ApiEnum Role { - get - { - if (!this._rawData.TryGetValue("role", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'role' cannot be null", - new System::ArgumentOutOfRangeException("role", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["role"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "role"); } + init { ModelBase.Set(this._rawData, "role", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -73,6 +34,9 @@ public override void Validate() public BetaMessageParam() { } + public BetaMessageParam(BetaMessageParam betaMessageParam) + : base(betaMessageParam) { } + public BetaMessageParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -86,6 +50,7 @@ public BetaMessageParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaMessageParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -96,6 +61,7 @@ IReadOnlyDictionary rawData class BetaMessageParamFromRaw : IFromRaw { + /// public BetaMessageParam FromRawUnchecked(IReadOnlyDictionary rawData) => BetaMessageParam.FromRawUnchecked(rawData); } @@ -132,12 +98,42 @@ public BetaMessageParamContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaContentBlockParams(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaContentBlockParams( [NotNullWhen(true)] out IReadOnlyList? value ) @@ -146,6 +142,26 @@ public bool TryPickBetaContentBlockParams( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action @string, System::Action> betaContentBlockParams @@ -166,6 +182,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match( System::Func @string, System::Func, T> betaContentBlockParams @@ -186,6 +223,16 @@ public T Match( public static implicit operator BetaMessageParamContent(List value) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -195,6 +242,16 @@ public void Validate() ); } } + + public virtual bool Equals(BetaMessageParamContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } } sealed class BetaMessageParamContentConverter : JsonConverter diff --git a/src/Anthropic/Models/Beta/Messages/BetaMessageTokensCount.cs b/src/Anthropic/Models/Beta/Messages/BetaMessageTokensCount.cs index 09dad3f5..3e43bbff 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMessageTokensCount.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMessageTokensCount.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Messages; @@ -19,21 +17,12 @@ public required BetaCountTokensContextManagementResponse? ContextManagement { get { - if (!this._rawData.TryGetValue("context_management", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["context_management"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "context_management" ); } + init { ModelBase.Set(this._rawData, "context_management", value); } } /// @@ -42,25 +31,11 @@ public required BetaCountTokensContextManagementResponse? ContextManagement /// public required long InputTokens { - get - { - if (!this._rawData.TryGetValue("input_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input_tokens' cannot be null", - new ArgumentOutOfRangeException("input_tokens", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "input_tokens"); } + init { ModelBase.Set(this._rawData, "input_tokens", value); } } + /// public override void Validate() { this.ContextManagement?.Validate(); @@ -69,6 +44,9 @@ public override void Validate() public BetaMessageTokensCount() { } + public BetaMessageTokensCount(BetaMessageTokensCount betaMessageTokensCount) + : base(betaMessageTokensCount) { } + public BetaMessageTokensCount(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -82,6 +60,7 @@ public BetaMessageTokensCount(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaMessageTokensCount FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -92,6 +71,7 @@ IReadOnlyDictionary rawData class BetaMessageTokensCountFromRaw : IFromRaw { + /// public BetaMessageTokensCount FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaMessageTokensCount.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaMetadata.cs b/src/Anthropic/Models/Beta/Messages/BetaMetadata.cs index 110a7390..e0f517ee 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaMetadata.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaMetadata.cs @@ -19,22 +19,11 @@ public sealed record class BetaMetadata : ModelBase /// public string? UserID { - get - { - if (!this._rawData.TryGetValue("user_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["user_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "user_id"); } + init { ModelBase.Set(this._rawData, "user_id", value); } } + /// public override void Validate() { _ = this.UserID; @@ -42,6 +31,9 @@ public override void Validate() public BetaMetadata() { } + public BetaMetadata(BetaMetadata betaMetadata) + : base(betaMetadata) { } + public BetaMetadata(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -55,6 +47,7 @@ public BetaMetadata(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaMetadata FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -63,6 +56,7 @@ public static BetaMetadata FromRawUnchecked(IReadOnlyDictionary { + /// public BetaMetadata FromRawUnchecked(IReadOnlyDictionary rawData) => BetaMetadata.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaOutputConfig.cs b/src/Anthropic/Models/Beta/Messages/BetaOutputConfig.cs index e6dbe419..c8b5c4df 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaOutputConfig.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaOutputConfig.cs @@ -17,25 +17,11 @@ public sealed record class BetaOutputConfig : ModelBase /// public ApiEnum? Effort { - get - { - if (!this._rawData.TryGetValue("effort", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["effort"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "effort"); } + init { ModelBase.Set(this._rawData, "effort", value); } } + /// public override void Validate() { this.Effort?.Validate(); @@ -43,6 +29,9 @@ public override void Validate() public BetaOutputConfig() { } + public BetaOutputConfig(BetaOutputConfig betaOutputConfig) + : base(betaOutputConfig) { } + public BetaOutputConfig(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -56,6 +45,7 @@ public BetaOutputConfig(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaOutputConfig FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -66,6 +56,7 @@ IReadOnlyDictionary rawData class BetaOutputConfigFromRaw : IFromRaw { + /// public BetaOutputConfig FromRawUnchecked(IReadOnlyDictionary rawData) => BetaOutputConfig.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaPlainTextSource.cs b/src/Anthropic/Models/Beta/Messages/BetaPlainTextSource.cs index 8502c462..a31db3ad 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaPlainTextSource.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaPlainTextSource.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,71 +13,23 @@ public sealed record class BetaPlainTextSource : ModelBase { public required string Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } public JsonElement MediaType { - get - { - if (!this._rawData.TryGetValue("media_type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'media_type' cannot be null", - new ArgumentOutOfRangeException("media_type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["media_type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "media_type"); } + init { ModelBase.Set(this._rawData, "media_type", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Data; @@ -103,6 +54,9 @@ public BetaPlainTextSource() this.Type = JsonSerializer.Deserialize("\"text\""); } + public BetaPlainTextSource(BetaPlainTextSource betaPlainTextSource) + : base(betaPlainTextSource) { } + public BetaPlainTextSource(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -119,6 +73,7 @@ public BetaPlainTextSource(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaPlainTextSource FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -136,6 +91,7 @@ public BetaPlainTextSource(string data) class BetaPlainTextSourceFromRaw : IFromRaw { + /// public BetaPlainTextSource FromRawUnchecked(IReadOnlyDictionary rawData) => BetaPlainTextSource.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockDelta.cs b/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockDelta.cs index eeeb32a6..74b4bb86 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockDelta.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockDelta.cs @@ -67,36 +67,134 @@ public BetaRawContentBlockDelta(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickText(out var value)) { + /// // `value` is of type `BetaTextDelta` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickText([NotNullWhen(true)] out BetaTextDelta? value) { value = this.Value as BetaTextDelta; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickInputJSON(out var value)) { + /// // `value` is of type `BetaInputJSONDelta` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickInputJSON([NotNullWhen(true)] out BetaInputJSONDelta? value) { value = this.Value as BetaInputJSONDelta; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitations(out var value)) { + /// // `value` is of type `BetaCitationsDelta` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitations([NotNullWhen(true)] out BetaCitationsDelta? value) { value = this.Value as BetaCitationsDelta; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickThinking(out var value)) { + /// // `value` is of type `BetaThinkingDelta` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickThinking([NotNullWhen(true)] out BetaThinkingDelta? value) { value = this.Value as BetaThinkingDelta; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickSignature(out var value)) { + /// // `value` is of type `BetaSignatureDelta` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickSignature([NotNullWhen(true)] out BetaSignatureDelta? value) { value = this.Value as BetaSignatureDelta; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaTextDelta value) => {...}, + /// (BetaInputJSONDelta value) => {...}, + /// (BetaCitationsDelta value) => {...}, + /// (BetaThinkingDelta value) => {...}, + /// (BetaSignatureDelta value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action text, System::Action inputJSON, @@ -129,6 +227,30 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaTextDelta value) => {...}, + /// (BetaInputJSONDelta value) => {...}, + /// (BetaCitationsDelta value) => {...}, + /// (BetaThinkingDelta value) => {...}, + /// (BetaSignatureDelta value) => {...} + /// ); + /// + /// + /// public T Match( System::Func text, System::Func inputJSON, @@ -163,6 +285,16 @@ public static implicit operator BetaRawContentBlockDelta(BetaCitationsDelta valu public static implicit operator BetaRawContentBlockDelta(BetaSignatureDelta value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -171,6 +303,23 @@ public void Validate() "Data did not match any variant of BetaRawContentBlockDelta" ); } + this.Switch( + (text) => text.Validate(), + (inputJSON) => inputJSON.Validate(), + (citations) => citations.Validate(), + (thinking) => thinking.Validate(), + (signature) => signature.Validate() + ); + } + + public virtual bool Equals(BetaRawContentBlockDelta? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockDeltaEvent.cs b/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockDeltaEvent.cs index 8647cb07..f66732d9 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockDeltaEvent.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockDeltaEvent.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,74 +15,23 @@ public sealed record class BetaRawContentBlockDeltaEvent : ModelBase { public required BetaRawContentBlockDelta Delta { - get - { - if (!this._rawData.TryGetValue("delta", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'delta' cannot be null", - new ArgumentOutOfRangeException("delta", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'delta' cannot be null", - new ArgumentNullException("delta") - ); - } - init - { - this._rawData["delta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "delta"); } + init { ModelBase.Set(this._rawData, "delta", value); } } public required long Index { - get - { - if (!this._rawData.TryGetValue("index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'index' cannot be null", - new ArgumentOutOfRangeException("index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "index"); } + init { ModelBase.Set(this._rawData, "index", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Delta.Validate(); @@ -104,6 +52,11 @@ public BetaRawContentBlockDeltaEvent() this.Type = JsonSerializer.Deserialize("\"content_block_delta\""); } + public BetaRawContentBlockDeltaEvent( + BetaRawContentBlockDeltaEvent betaRawContentBlockDeltaEvent + ) + : base(betaRawContentBlockDeltaEvent) { } + public BetaRawContentBlockDeltaEvent(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -119,6 +72,7 @@ public BetaRawContentBlockDeltaEvent(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaRawContentBlockDeltaEvent FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -129,6 +83,7 @@ IReadOnlyDictionary rawData class BetaRawContentBlockDeltaEventFromRaw : IFromRaw { + /// public BetaRawContentBlockDeltaEvent FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaRawContentBlockDeltaEvent.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockStartEvent.cs b/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockStartEvent.cs index 817b32da..4deff8e1 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockStartEvent.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockStartEvent.cs @@ -19,74 +19,23 @@ public sealed record class BetaRawContentBlockStartEvent : ModelBase /// public required ContentBlock ContentBlock { - get - { - if (!this._rawData.TryGetValue("content_block", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content_block' cannot be null", - new System::ArgumentOutOfRangeException( - "content_block", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'content_block' cannot be null", - new System::ArgumentNullException("content_block") - ); - } - init - { - this._rawData["content_block"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "content_block"); } + init { ModelBase.Set(this._rawData, "content_block", value); } } public required long Index { - get - { - if (!this._rawData.TryGetValue("index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'index' cannot be null", - new System::ArgumentOutOfRangeException("index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "index"); } + init { ModelBase.Set(this._rawData, "index", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.ContentBlock.Validate(); @@ -107,6 +56,11 @@ public BetaRawContentBlockStartEvent() this.Type = JsonSerializer.Deserialize("\"content_block_start\""); } + public BetaRawContentBlockStartEvent( + BetaRawContentBlockStartEvent betaRawContentBlockStartEvent + ) + : base(betaRawContentBlockStartEvent) { } + public BetaRawContentBlockStartEvent(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -122,6 +76,7 @@ public BetaRawContentBlockStartEvent(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaRawContentBlockStartEvent FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -132,6 +87,7 @@ IReadOnlyDictionary rawData class BetaRawContentBlockStartEventFromRaw : IFromRaw { + /// public BetaRawContentBlockStartEvent FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaRawContentBlockStartEvent.FromRawUnchecked(rawData); @@ -310,18 +266,63 @@ public ContentBlock(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaText(out var value)) { + /// // `value` is of type `BetaTextBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaText([NotNullWhen(true)] out BetaTextBlock? value) { value = this.Value as BetaTextBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaThinking(out var value)) { + /// // `value` is of type `BetaThinkingBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaThinking([NotNullWhen(true)] out BetaThinkingBlock? value) { value = this.Value as BetaThinkingBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaRedactedThinking(out var value)) { + /// // `value` is of type `BetaRedactedThinkingBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaRedactedThinking( [NotNullWhen(true)] out BetaRedactedThinkingBlock? value ) @@ -330,18 +331,63 @@ public bool TryPickBetaRedactedThinking( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolUse(out var value)) { + /// // `value` is of type `BetaToolUseBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolUse([NotNullWhen(true)] out BetaToolUseBlock? value) { value = this.Value as BetaToolUseBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaServerToolUse(out var value)) { + /// // `value` is of type `BetaServerToolUseBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaServerToolUse([NotNullWhen(true)] out BetaServerToolUseBlock? value) { value = this.Value as BetaServerToolUseBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaWebSearchToolResult(out var value)) { + /// // `value` is of type `BetaWebSearchToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaWebSearchToolResult( [NotNullWhen(true)] out BetaWebSearchToolResultBlock? value ) @@ -350,6 +396,21 @@ public bool TryPickBetaWebSearchToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaWebFetchToolResult(out var value)) { + /// // `value` is of type `BetaWebFetchToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaWebFetchToolResult( [NotNullWhen(true)] out BetaWebFetchToolResultBlock? value ) @@ -358,6 +419,21 @@ public bool TryPickBetaWebFetchToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaCodeExecutionToolResult(out var value)) { + /// // `value` is of type `BetaCodeExecutionToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaCodeExecutionToolResult( [NotNullWhen(true)] out BetaCodeExecutionToolResultBlock? value ) @@ -366,6 +442,21 @@ public bool TryPickBetaCodeExecutionToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaBashCodeExecutionToolResult(out var value)) { + /// // `value` is of type `BetaBashCodeExecutionToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaBashCodeExecutionToolResult( [NotNullWhen(true)] out BetaBashCodeExecutionToolResultBlock? value ) @@ -374,6 +465,21 @@ public bool TryPickBetaBashCodeExecutionToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaTextEditorCodeExecutionToolResult(out var value)) { + /// // `value` is of type `BetaTextEditorCodeExecutionToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaTextEditorCodeExecutionToolResult( [NotNullWhen(true)] out BetaTextEditorCodeExecutionToolResultBlock? value ) @@ -382,6 +488,21 @@ public bool TryPickBetaTextEditorCodeExecutionToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolSearchToolResult(out var value)) { + /// // `value` is of type `BetaToolSearchToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolSearchToolResult( [NotNullWhen(true)] out BetaToolSearchToolResultBlock? value ) @@ -390,24 +511,101 @@ public bool TryPickBetaToolSearchToolResult( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaMCPToolUse(out var value)) { + /// // `value` is of type `BetaMCPToolUseBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaMCPToolUse([NotNullWhen(true)] out BetaMCPToolUseBlock? value) { value = this.Value as BetaMCPToolUseBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaMCPToolResult(out var value)) { + /// // `value` is of type `BetaMCPToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaMCPToolResult([NotNullWhen(true)] out BetaMCPToolResultBlock? value) { value = this.Value as BetaMCPToolResultBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaContainerUpload(out var value)) { + /// // `value` is of type `BetaContainerUploadBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaContainerUpload([NotNullWhen(true)] out BetaContainerUploadBlock? value) { value = this.Value as BetaContainerUploadBlock; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaTextBlock value) => {...}, + /// (BetaThinkingBlock value) => {...}, + /// (BetaRedactedThinkingBlock value) => {...}, + /// (BetaToolUseBlock value) => {...}, + /// (BetaServerToolUseBlock value) => {...}, + /// (BetaWebSearchToolResultBlock value) => {...}, + /// (BetaWebFetchToolResultBlock value) => {...}, + /// (BetaCodeExecutionToolResultBlock value) => {...}, + /// (BetaBashCodeExecutionToolResultBlock value) => {...}, + /// (BetaTextEditorCodeExecutionToolResultBlock value) => {...}, + /// (BetaToolSearchToolResultBlock value) => {...}, + /// (BetaMCPToolUseBlock value) => {...}, + /// (BetaMCPToolResultBlock value) => {...}, + /// (BetaContainerUploadBlock value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaText, System::Action betaThinking, @@ -476,6 +674,39 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaTextBlock value) => {...}, + /// (BetaThinkingBlock value) => {...}, + /// (BetaRedactedThinkingBlock value) => {...}, + /// (BetaToolUseBlock value) => {...}, + /// (BetaServerToolUseBlock value) => {...}, + /// (BetaWebSearchToolResultBlock value) => {...}, + /// (BetaWebFetchToolResultBlock value) => {...}, + /// (BetaCodeExecutionToolResultBlock value) => {...}, + /// (BetaBashCodeExecutionToolResultBlock value) => {...}, + /// (BetaTextEditorCodeExecutionToolResultBlock value) => {...}, + /// (BetaToolSearchToolResultBlock value) => {...}, + /// (BetaMCPToolUseBlock value) => {...}, + /// (BetaMCPToolResultBlock value) => {...}, + /// (BetaContainerUploadBlock value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaText, System::Func betaThinking, @@ -551,6 +782,16 @@ BetaTextEditorCodeExecutionToolResultBlock value public static implicit operator ContentBlock(BetaContainerUploadBlock value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -559,6 +800,33 @@ public void Validate() "Data did not match any variant of ContentBlock" ); } + this.Switch( + (betaText) => betaText.Validate(), + (betaThinking) => betaThinking.Validate(), + (betaRedactedThinking) => betaRedactedThinking.Validate(), + (betaToolUse) => betaToolUse.Validate(), + (betaServerToolUse) => betaServerToolUse.Validate(), + (betaWebSearchToolResult) => betaWebSearchToolResult.Validate(), + (betaWebFetchToolResult) => betaWebFetchToolResult.Validate(), + (betaCodeExecutionToolResult) => betaCodeExecutionToolResult.Validate(), + (betaBashCodeExecutionToolResult) => betaBashCodeExecutionToolResult.Validate(), + (betaTextEditorCodeExecutionToolResult) => + betaTextEditorCodeExecutionToolResult.Validate(), + (betaToolSearchToolResult) => betaToolSearchToolResult.Validate(), + (betaMCPToolUse) => betaMCPToolUse.Validate(), + (betaMCPToolResult) => betaMCPToolResult.Validate(), + (betaContainerUpload) => betaContainerUpload.Validate() + ); + } + + public virtual bool Equals(ContentBlock? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockStopEvent.cs b/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockStopEvent.cs index a1f92849..6e6fcc31 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockStopEvent.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaRawContentBlockStopEvent.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,46 +15,17 @@ public sealed record class BetaRawContentBlockStopEvent : ModelBase { public required long Index { - get - { - if (!this._rawData.TryGetValue("index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'index' cannot be null", - new ArgumentOutOfRangeException("index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "index"); } + init { ModelBase.Set(this._rawData, "index", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Index; @@ -75,6 +45,9 @@ public BetaRawContentBlockStopEvent() this.Type = JsonSerializer.Deserialize("\"content_block_stop\""); } + public BetaRawContentBlockStopEvent(BetaRawContentBlockStopEvent betaRawContentBlockStopEvent) + : base(betaRawContentBlockStopEvent) { } + public BetaRawContentBlockStopEvent(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -90,6 +63,7 @@ public BetaRawContentBlockStopEvent(IReadOnlyDictionary raw } #pragma warning restore CS8618 + /// public static BetaRawContentBlockStopEvent FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -107,6 +81,7 @@ public BetaRawContentBlockStopEvent(long index) class BetaRawContentBlockStopEventFromRaw : IFromRaw { + /// public BetaRawContentBlockStopEvent FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaRawContentBlockStopEvent.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaRawMessageDeltaEvent.cs b/src/Anthropic/Models/Beta/Messages/BetaRawMessageDeltaEvent.cs index 30aee814..28f77847 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaRawMessageDeltaEvent.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaRawMessageDeltaEvent.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,67 +18,24 @@ public required BetaContextManagementResponse? ContextManagement { get { - if (!this._rawData.TryGetValue("context_management", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["context_management"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "context_management" ); } + init { ModelBase.Set(this._rawData, "context_management", value); } } public required Delta Delta { - get - { - if (!this._rawData.TryGetValue("delta", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'delta' cannot be null", - new ArgumentOutOfRangeException("delta", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'delta' cannot be null", - new ArgumentNullException("delta") - ); - } - init - { - this._rawData["delta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "delta"); } + init { ModelBase.Set(this._rawData, "delta", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -101,32 +57,11 @@ public JsonElement Type /// public required BetaMessageDeltaUsage Usage { - get - { - if (!this._rawData.TryGetValue("usage", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'usage' cannot be null", - new ArgumentOutOfRangeException("usage", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'usage' cannot be null", - new ArgumentNullException("usage") - ); - } - init - { - this._rawData["usage"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "usage"); } + init { ModelBase.Set(this._rawData, "usage", value); } } + /// public override void Validate() { this.ContextManagement?.Validate(); @@ -148,6 +83,9 @@ public BetaRawMessageDeltaEvent() this.Type = JsonSerializer.Deserialize("\"message_delta\""); } + public BetaRawMessageDeltaEvent(BetaRawMessageDeltaEvent betaRawMessageDeltaEvent) + : base(betaRawMessageDeltaEvent) { } + public BetaRawMessageDeltaEvent(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -163,6 +101,7 @@ public BetaRawMessageDeltaEvent(IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaRawMessageDeltaEvent FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -173,6 +112,7 @@ IReadOnlyDictionary rawData class BetaRawMessageDeltaEventFromRaw : IFromRaw { + /// public BetaRawMessageDeltaEvent FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaRawMessageDeltaEvent.FromRawUnchecked(rawData); @@ -186,61 +126,29 @@ public sealed record class Delta : ModelBase /// public required BetaContainer? Container { - get - { - if (!this._rawData.TryGetValue("container", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["container"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "container"); } + init { ModelBase.Set(this._rawData, "container", value); } } public required ApiEnum? StopReason { get { - if (!this._rawData.TryGetValue("stop_reason", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["stop_reason"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawData, + "stop_reason" ); } + init { ModelBase.Set(this._rawData, "stop_reason", value); } } public required string? StopSequence { - get - { - if (!this._rawData.TryGetValue("stop_sequence", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["stop_sequence"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "stop_sequence"); } + init { ModelBase.Set(this._rawData, "stop_sequence", value); } } + /// public override void Validate() { this.Container?.Validate(); @@ -250,6 +158,9 @@ public override void Validate() public Delta() { } + public Delta(Delta delta) + : base(delta) { } + public Delta(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -263,6 +174,7 @@ public Delta(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static Delta FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -271,6 +183,7 @@ public static Delta FromRawUnchecked(IReadOnlyDictionary ra class DeltaFromRaw : IFromRaw { + /// public Delta FromRawUnchecked(IReadOnlyDictionary rawData) => Delta.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaRawMessageStartEvent.cs b/src/Anthropic/Models/Beta/Messages/BetaRawMessageStartEvent.cs index f96f0be4..0912593f 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaRawMessageStartEvent.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaRawMessageStartEvent.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaRawMessageStartEvent : ModelBase { public required BetaMessage Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Message.Validate(); @@ -77,6 +43,9 @@ public BetaRawMessageStartEvent() this.Type = JsonSerializer.Deserialize("\"message_start\""); } + public BetaRawMessageStartEvent(BetaRawMessageStartEvent betaRawMessageStartEvent) + : base(betaRawMessageStartEvent) { } + public BetaRawMessageStartEvent(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaRawMessageStartEvent(IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaRawMessageStartEvent FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public BetaRawMessageStartEvent(BetaMessage message) class BetaRawMessageStartEventFromRaw : IFromRaw { + /// public BetaRawMessageStartEvent FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaRawMessageStartEvent.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaRawMessageStopEvent.cs b/src/Anthropic/Models/Beta/Messages/BetaRawMessageStopEvent.cs index 8e5f9a3c..f3d10115 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaRawMessageStopEvent.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaRawMessageStopEvent.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,25 +13,11 @@ public sealed record class BetaRawMessageStopEvent : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { if ( @@ -51,6 +36,9 @@ public BetaRawMessageStopEvent() this.Type = JsonSerializer.Deserialize("\"message_stop\""); } + public BetaRawMessageStopEvent(BetaRawMessageStopEvent betaRawMessageStopEvent) + : base(betaRawMessageStopEvent) { } + public BetaRawMessageStopEvent(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -66,6 +54,7 @@ public BetaRawMessageStopEvent(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaRawMessageStopEvent FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -76,6 +65,7 @@ IReadOnlyDictionary rawData class BetaRawMessageStopEventFromRaw : IFromRaw { + /// public BetaRawMessageStopEvent FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaRawMessageStopEvent.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaRawMessageStreamEvent.cs b/src/Anthropic/Models/Beta/Messages/BetaRawMessageStreamEvent.cs index 02a86b2e..9bc8ddfa 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaRawMessageStreamEvent.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaRawMessageStreamEvent.cs @@ -89,24 +89,84 @@ public BetaRawMessageStreamEvent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickStart(out var value)) { + /// // `value` is of type `BetaRawMessageStartEvent` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickStart([NotNullWhen(true)] out BetaRawMessageStartEvent? value) { value = this.Value as BetaRawMessageStartEvent; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickDelta(out var value)) { + /// // `value` is of type `BetaRawMessageDeltaEvent` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickDelta([NotNullWhen(true)] out BetaRawMessageDeltaEvent? value) { value = this.Value as BetaRawMessageDeltaEvent; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickStop(out var value)) { + /// // `value` is of type `BetaRawMessageStopEvent` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickStop([NotNullWhen(true)] out BetaRawMessageStopEvent? value) { value = this.Value as BetaRawMessageStopEvent; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickContentBlockStart(out var value)) { + /// // `value` is of type `BetaRawContentBlockStartEvent` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickContentBlockStart( [NotNullWhen(true)] out BetaRawContentBlockStartEvent? value ) @@ -115,6 +175,21 @@ public bool TryPickContentBlockStart( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickContentBlockDelta(out var value)) { + /// // `value` is of type `BetaRawContentBlockDeltaEvent` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickContentBlockDelta( [NotNullWhen(true)] out BetaRawContentBlockDeltaEvent? value ) @@ -123,12 +198,51 @@ public bool TryPickContentBlockDelta( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickContentBlockStop(out var value)) { + /// // `value` is of type `BetaRawContentBlockStopEvent` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickContentBlockStop([NotNullWhen(true)] out BetaRawContentBlockStopEvent? value) { value = this.Value as BetaRawContentBlockStopEvent; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaRawMessageStartEvent value) => {...}, + /// (BetaRawMessageDeltaEvent value) => {...}, + /// (BetaRawMessageStopEvent value) => {...}, + /// (BetaRawContentBlockStartEvent value) => {...}, + /// (BetaRawContentBlockDeltaEvent value) => {...}, + /// (BetaRawContentBlockStopEvent value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action start, System::Action delta, @@ -165,6 +279,31 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaRawMessageStartEvent value) => {...}, + /// (BetaRawMessageDeltaEvent value) => {...}, + /// (BetaRawMessageStopEvent value) => {...}, + /// (BetaRawContentBlockStartEvent value) => {...}, + /// (BetaRawContentBlockDeltaEvent value) => {...}, + /// (BetaRawContentBlockStopEvent value) => {...} + /// ); + /// + /// + /// public T Match( System::Func start, System::Func delta, @@ -208,6 +347,16 @@ BetaRawContentBlockDeltaEvent value public static implicit operator BetaRawMessageStreamEvent(BetaRawContentBlockStopEvent value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -216,6 +365,24 @@ public void Validate() "Data did not match any variant of BetaRawMessageStreamEvent" ); } + this.Switch( + (start) => start.Validate(), + (delta) => delta.Validate(), + (stop) => stop.Validate(), + (contentBlockStart) => contentBlockStart.Validate(), + (contentBlockDelta) => contentBlockDelta.Validate(), + (contentBlockStop) => contentBlockStop.Validate() + ); + } + + public virtual bool Equals(BetaRawMessageStreamEvent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaRedactedThinkingBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaRedactedThinkingBlock.cs index 0e4405b5..96df5ef4 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaRedactedThinkingBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaRedactedThinkingBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaRedactedThinkingBlock : ModelBase { public required string Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Data; @@ -77,6 +43,9 @@ public BetaRedactedThinkingBlock() this.Type = JsonSerializer.Deserialize("\"redacted_thinking\""); } + public BetaRedactedThinkingBlock(BetaRedactedThinkingBlock betaRedactedThinkingBlock) + : base(betaRedactedThinkingBlock) { } + public BetaRedactedThinkingBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaRedactedThinkingBlock(IReadOnlyDictionary rawDat } #pragma warning restore CS8618 + /// public static BetaRedactedThinkingBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public BetaRedactedThinkingBlock(string data) class BetaRedactedThinkingBlockFromRaw : IFromRaw { + /// public BetaRedactedThinkingBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaRedactedThinkingBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaRedactedThinkingBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaRedactedThinkingBlockParam.cs index ecf2fcbc..f7c7ebcc 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaRedactedThinkingBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaRedactedThinkingBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,50 +15,17 @@ public sealed record class BetaRedactedThinkingBlockParam : ModelBase { public required string Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Data; @@ -79,6 +45,11 @@ public BetaRedactedThinkingBlockParam() this.Type = JsonSerializer.Deserialize("\"redacted_thinking\""); } + public BetaRedactedThinkingBlockParam( + BetaRedactedThinkingBlockParam betaRedactedThinkingBlockParam + ) + : base(betaRedactedThinkingBlockParam) { } + public BetaRedactedThinkingBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -94,6 +65,7 @@ public BetaRedactedThinkingBlockParam(IReadOnlyDictionary r } #pragma warning restore CS8618 + /// public static BetaRedactedThinkingBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -111,6 +83,7 @@ public BetaRedactedThinkingBlockParam(string data) class BetaRedactedThinkingBlockParamFromRaw : IFromRaw { + /// public BetaRedactedThinkingBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaRedactedThinkingBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaRequestDocumentBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaRequestDocumentBlock.cs index 79f14f1f..e617d9e8 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaRequestDocumentBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaRequestDocumentBlock.cs @@ -16,49 +16,18 @@ public required BetaRequestDocumentBlockSource Source { get { - if (!this._rawData.TryGetValue("source", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'source' cannot be null", - new System::ArgumentOutOfRangeException("source", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'source' cannot be null", - new System::ArgumentNullException("source") - ); - } - init - { - this._rawData["source"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "source" ); } + init { ModelBase.Set(this._rawData, "source", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -68,80 +37,36 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } public BetaCitationsConfigParam? Citations { get { - if (!this._rawData.TryGetValue("citations", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["citations"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "citations"); } + init { ModelBase.Set(this._rawData, "citations", value); } } public string? Context { - get - { - if (!this._rawData.TryGetValue("context", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["context"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "context"); } + init { ModelBase.Set(this._rawData, "context", value); } } public string? Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } + /// public override void Validate() { this.Source.Validate(); @@ -165,6 +90,9 @@ public BetaRequestDocumentBlock() this.Type = JsonSerializer.Deserialize("\"document\""); } + public BetaRequestDocumentBlock(BetaRequestDocumentBlock betaRequestDocumentBlock) + : base(betaRequestDocumentBlock) { } + public BetaRequestDocumentBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -180,6 +108,7 @@ public BetaRequestDocumentBlock(IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaRequestDocumentBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -197,6 +126,7 @@ public BetaRequestDocumentBlock(BetaRequestDocumentBlockSource source) class BetaRequestDocumentBlockFromRaw : IFromRaw { + /// public BetaRequestDocumentBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaRequestDocumentBlock.FromRawUnchecked(rawData); @@ -291,36 +221,134 @@ public BetaRequestDocumentBlockSource(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaBase64PDF(out var value)) { + /// // `value` is of type `BetaBase64PDFSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaBase64PDF([NotNullWhen(true)] out BetaBase64PDFSource? value) { value = this.Value as BetaBase64PDFSource; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaPlainText(out var value)) { + /// // `value` is of type `BetaPlainTextSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaPlainText([NotNullWhen(true)] out BetaPlainTextSource? value) { value = this.Value as BetaPlainTextSource; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaContentBlock(out var value)) { + /// // `value` is of type `BetaContentBlockSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaContentBlock([NotNullWhen(true)] out BetaContentBlockSource? value) { value = this.Value as BetaContentBlockSource; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaURLPDF(out var value)) { + /// // `value` is of type `BetaURLPDFSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaURLPDF([NotNullWhen(true)] out BetaURLPDFSource? value) { value = this.Value as BetaURLPDFSource; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaFileDocument(out var value)) { + /// // `value` is of type `BetaFileDocumentSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaFileDocument([NotNullWhen(true)] out BetaFileDocumentSource? value) { value = this.Value as BetaFileDocumentSource; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaBase64PDFSource value) => {...}, + /// (BetaPlainTextSource value) => {...}, + /// (BetaContentBlockSource value) => {...}, + /// (BetaURLPDFSource value) => {...}, + /// (BetaFileDocumentSource value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaBase64PDF, System::Action betaPlainText, @@ -353,6 +381,30 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaBase64PDFSource value) => {...}, + /// (BetaPlainTextSource value) => {...}, + /// (BetaContentBlockSource value) => {...}, + /// (BetaURLPDFSource value) => {...}, + /// (BetaFileDocumentSource value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaBase64PDF, System::Func betaPlainText, @@ -389,6 +441,16 @@ public static implicit operator BetaRequestDocumentBlockSource(BetaURLPDFSource public static implicit operator BetaRequestDocumentBlockSource(BetaFileDocumentSource value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -397,6 +459,23 @@ public void Validate() "Data did not match any variant of BetaRequestDocumentBlockSource" ); } + this.Switch( + (betaBase64PDF) => betaBase64PDF.Validate(), + (betaPlainText) => betaPlainText.Validate(), + (betaContentBlock) => betaContentBlock.Validate(), + (betaURLPDF) => betaURLPDF.Validate(), + (betaFileDocument) => betaFileDocument.Validate() + ); + } + + public virtual bool Equals(BetaRequestDocumentBlockSource? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaRequestMCPServerToolConfiguration.cs b/src/Anthropic/Models/Beta/Messages/BetaRequestMCPServerToolConfiguration.cs index a485f10a..f01cf0d5 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaRequestMCPServerToolConfiguration.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaRequestMCPServerToolConfiguration.cs @@ -17,40 +17,17 @@ public sealed record class BetaRequestMCPServerToolConfiguration : ModelBase { public IReadOnlyList? AllowedTools { - get - { - if (!this._rawData.TryGetValue("allowed_tools", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["allowed_tools"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "allowed_tools"); } + init { ModelBase.Set(this._rawData, "allowed_tools", value); } } public bool? Enabled { - get - { - if (!this._rawData.TryGetValue("enabled", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["enabled"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "enabled"); } + init { ModelBase.Set(this._rawData, "enabled", value); } } + /// public override void Validate() { _ = this.AllowedTools; @@ -59,6 +36,11 @@ public override void Validate() public BetaRequestMCPServerToolConfiguration() { } + public BetaRequestMCPServerToolConfiguration( + BetaRequestMCPServerToolConfiguration betaRequestMCPServerToolConfiguration + ) + : base(betaRequestMCPServerToolConfiguration) { } + public BetaRequestMCPServerToolConfiguration(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -72,6 +54,7 @@ public BetaRequestMCPServerToolConfiguration(IReadOnlyDictionary public static BetaRequestMCPServerToolConfiguration FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -82,6 +65,7 @@ IReadOnlyDictionary rawData class BetaRequestMCPServerToolConfigurationFromRaw : IFromRaw { + /// public BetaRequestMCPServerToolConfiguration FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaRequestMCPServerToolConfiguration.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaRequestMCPServerURLDefinition.cs b/src/Anthropic/Models/Beta/Messages/BetaRequestMCPServerURLDefinition.cs index 3e54204b..7980a72e 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaRequestMCPServerURLDefinition.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaRequestMCPServerURLDefinition.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,114 +18,41 @@ public sealed record class BetaRequestMCPServerURLDefinition : ModelBase { public required string Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentNullException("name") - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required string URL { - get - { - if (!this._rawData.TryGetValue("url", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentOutOfRangeException("url", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentNullException("url") - ); - } - init - { - this._rawData["url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "url"); } + init { ModelBase.Set(this._rawData, "url", value); } } public string? AuthorizationToken { - get - { - if (!this._rawData.TryGetValue("authorization_token", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["authorization_token"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "authorization_token"); } + init { ModelBase.Set(this._rawData, "authorization_token", value); } } public BetaRequestMCPServerToolConfiguration? ToolConfiguration { get { - if (!this._rawData.TryGetValue("tool_configuration", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["tool_configuration"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "tool_configuration" ); } + init { ModelBase.Set(this._rawData, "tool_configuration", value); } } + /// public override void Validate() { _ = this.Name; @@ -144,6 +70,11 @@ public BetaRequestMCPServerURLDefinition() this.Type = JsonSerializer.Deserialize("\"url\""); } + public BetaRequestMCPServerURLDefinition( + BetaRequestMCPServerURLDefinition betaRequestMCPServerURLDefinition + ) + : base(betaRequestMCPServerURLDefinition) { } + public BetaRequestMCPServerURLDefinition(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -159,6 +90,7 @@ public BetaRequestMCPServerURLDefinition(IReadOnlyDictionary public static BetaRequestMCPServerURLDefinition FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -169,6 +101,7 @@ IReadOnlyDictionary rawData class BetaRequestMCPServerURLDefinitionFromRaw : IFromRaw { + /// public BetaRequestMCPServerURLDefinition FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaRequestMCPServerURLDefinition.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaRequestMCPToolResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaRequestMCPToolResultBlockParam.cs index ed0a110d..54c8e108 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaRequestMCPToolResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaRequestMCPToolResultBlockParam.cs @@ -20,51 +20,14 @@ public sealed record class BetaRequestMCPToolResultBlockParam : ModelBase { public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentOutOfRangeException( - "tool_use_id", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -74,33 +37,21 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } public BetaRequestMCPToolResultBlockParamContent? Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "content" ); } init @@ -110,22 +61,13 @@ public BetaRequestMCPToolResultBlockParamContent? Content return; } - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "content", value); } } public bool? IsError { - get - { - if (!this._rawData.TryGetValue("is_error", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "is_error"); } init { if (value == null) @@ -133,13 +75,11 @@ public bool? IsError return; } - this._rawData["is_error"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "is_error", value); } } + /// public override void Validate() { _ = this.ToolUseID; @@ -162,6 +102,11 @@ public BetaRequestMCPToolResultBlockParam() this.Type = JsonSerializer.Deserialize("\"mcp_tool_result\""); } + public BetaRequestMCPToolResultBlockParam( + BetaRequestMCPToolResultBlockParam betaRequestMCPToolResultBlockParam + ) + : base(betaRequestMCPToolResultBlockParam) { } + public BetaRequestMCPToolResultBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -177,6 +122,7 @@ public BetaRequestMCPToolResultBlockParam(IReadOnlyDictionary public static BetaRequestMCPToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -194,6 +140,7 @@ public BetaRequestMCPToolResultBlockParam(string toolUseID) class BetaRequestMCPToolResultBlockParamFromRaw : IFromRaw { + /// public BetaRequestMCPToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaRequestMCPToolResultBlockParam.FromRawUnchecked(rawData); @@ -231,12 +178,42 @@ public BetaRequestMCPToolResultBlockParamContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaMCPToolResultBlockParam(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaMCPToolResultBlockParam( [NotNullWhen(true)] out IReadOnlyList? value ) @@ -245,6 +222,26 @@ public bool TryPickBetaMCPToolResultBlockParam( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action @string, System::Action> betaMCPToolResultBlockParamContent @@ -265,6 +262,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match( System::Func @string, System::Func, T> betaMCPToolResultBlockParamContent @@ -287,6 +305,16 @@ public static implicit operator BetaRequestMCPToolResultBlockParamContent( List value ) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -296,6 +324,16 @@ public void Validate() ); } } + + public virtual bool Equals(BetaRequestMCPToolResultBlockParamContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } } sealed class BetaRequestMCPToolResultBlockParamContentConverter diff --git a/src/Anthropic/Models/Beta/Messages/BetaSearchResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaSearchResultBlockParam.cs index 6c6c273a..df6b2a26 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaSearchResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaSearchResultBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,101 +15,26 @@ public sealed record class BetaSearchResultBlockParam : ModelBase { public required IReadOnlyList Content { - get - { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "content"); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string Source { - get - { - if (!this._rawData.TryGetValue("source", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentOutOfRangeException("source", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentNullException("source") - ); - } - init - { - this._rawData["source"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "source"); } + init { ModelBase.Set(this._rawData, "source", value); } } public required string Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'title' cannot be null", - new ArgumentOutOfRangeException("title", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'title' cannot be null", - new ArgumentNullException("title") - ); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -120,34 +44,19 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } public BetaCitationsConfigParam? Citations { get { - if (!this._rawData.TryGetValue("citations", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "citations"); } init { @@ -156,13 +65,11 @@ public BetaCitationsConfigParam? Citations return; } - this._rawData["citations"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "citations", value); } } + /// public override void Validate() { foreach (var item in this.Content) @@ -189,6 +96,9 @@ public BetaSearchResultBlockParam() this.Type = JsonSerializer.Deserialize("\"search_result\""); } + public BetaSearchResultBlockParam(BetaSearchResultBlockParam betaSearchResultBlockParam) + : base(betaSearchResultBlockParam) { } + public BetaSearchResultBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -204,6 +114,7 @@ public BetaSearchResultBlockParam(IReadOnlyDictionary rawDa } #pragma warning restore CS8618 + /// public static BetaSearchResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -214,6 +125,7 @@ IReadOnlyDictionary rawData class BetaSearchResultBlockParamFromRaw : IFromRaw { + /// public BetaSearchResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaSearchResultBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaServerToolCaller.cs b/src/Anthropic/Models/Beta/Messages/BetaServerToolCaller.cs index 0b2ec307..44b14773 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaServerToolCaller.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaServerToolCaller.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -17,50 +16,17 @@ public sealed record class BetaServerToolCaller : ModelBase { public required string ToolID { - get - { - if (!this._rawData.TryGetValue("tool_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_id' cannot be null", - new ArgumentOutOfRangeException("tool_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_id' cannot be null", - new ArgumentNullException("tool_id") - ); - } - init - { - this._rawData["tool_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_id"); } + init { ModelBase.Set(this._rawData, "tool_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ToolID; @@ -80,6 +46,9 @@ public BetaServerToolCaller() this.Type = JsonSerializer.Deserialize("\"code_execution_20250825\""); } + public BetaServerToolCaller(BetaServerToolCaller betaServerToolCaller) + : base(betaServerToolCaller) { } + public BetaServerToolCaller(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -95,6 +64,7 @@ public BetaServerToolCaller(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaServerToolCaller FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -112,6 +82,7 @@ public BetaServerToolCaller(string toolID) class BetaServerToolCallerFromRaw : IFromRaw { + /// public BetaServerToolCaller FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaServerToolCaller.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaServerToolUsage.cs b/src/Anthropic/Models/Beta/Messages/BetaServerToolUsage.cs index 026ff14b..58641735 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaServerToolUsage.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaServerToolUsage.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Messages; @@ -17,26 +15,8 @@ public sealed record class BetaServerToolUsage : ModelBase /// public required long WebFetchRequests { - get - { - if (!this._rawData.TryGetValue("web_fetch_requests", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'web_fetch_requests' cannot be null", - new ArgumentOutOfRangeException( - "web_fetch_requests", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["web_fetch_requests"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "web_fetch_requests"); } + init { ModelBase.Set(this._rawData, "web_fetch_requests", value); } } /// @@ -44,28 +24,11 @@ public required long WebFetchRequests /// public required long WebSearchRequests { - get - { - if (!this._rawData.TryGetValue("web_search_requests", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'web_search_requests' cannot be null", - new ArgumentOutOfRangeException( - "web_search_requests", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["web_search_requests"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "web_search_requests"); } + init { ModelBase.Set(this._rawData, "web_search_requests", value); } } + /// public override void Validate() { _ = this.WebFetchRequests; @@ -74,6 +37,9 @@ public override void Validate() public BetaServerToolUsage() { } + public BetaServerToolUsage(BetaServerToolUsage betaServerToolUsage) + : base(betaServerToolUsage) { } + public BetaServerToolUsage(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -87,6 +53,7 @@ public BetaServerToolUsage(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaServerToolUsage FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -97,6 +64,7 @@ IReadOnlyDictionary rawData class BetaServerToolUsageFromRaw : IFromRaw { + /// public BetaServerToolUsage FromRawUnchecked(IReadOnlyDictionary rawData) => BetaServerToolUsage.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaServerToolUseBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaServerToolUseBlock.cs index 386eea88..58c70d2d 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaServerToolUseBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaServerToolUseBlock.cs @@ -14,27 +14,8 @@ public sealed record class BetaServerToolUseBlock : ModelBase { public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new System::ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new System::ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -42,102 +23,35 @@ public required string ID /// public required Caller Caller { - get - { - if (!this._rawData.TryGetValue("caller", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'caller' cannot be null", - new System::ArgumentOutOfRangeException("caller", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'caller' cannot be null", - new System::ArgumentNullException("caller") - ); - } - init - { - this._rawData["caller"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "caller"); } + init { ModelBase.Set(this._rawData, "caller", value); } } public required IReadOnlyDictionary Input { get { - if (!this._rawData.TryGetValue("input", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input' cannot be null", - new System::ArgumentOutOfRangeException("input", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'input' cannot be null", - new System::ArgumentNullException("input") - ); - } - init - { - this._rawData["input"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "input" ); } + init { ModelBase.Set(this._rawData, "input", value); } } public required ApiEnum Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ID; @@ -160,6 +74,9 @@ public BetaServerToolUseBlock() this.Type = JsonSerializer.Deserialize("\"server_tool_use\""); } + public BetaServerToolUseBlock(BetaServerToolUseBlock betaServerToolUseBlock) + : base(betaServerToolUseBlock) { } + public BetaServerToolUseBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -175,6 +92,7 @@ public BetaServerToolUseBlock(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaServerToolUseBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -185,6 +103,7 @@ IReadOnlyDictionary rawData class BetaServerToolUseBlockFromRaw : IFromRaw { + /// public BetaServerToolUseBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaServerToolUseBlock.FromRawUnchecked(rawData); @@ -227,18 +146,68 @@ public Caller(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaDirect(out var value)) { + /// // `value` is of type `BetaDirectCaller` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaDirect([NotNullWhen(true)] out BetaDirectCaller? value) { value = this.Value as BetaDirectCaller; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaServerTool(out var value)) { + /// // `value` is of type `BetaServerToolCaller` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaServerTool([NotNullWhen(true)] out BetaServerToolCaller? value) { value = this.Value as BetaServerToolCaller; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaDirectCaller value) => {...}, + /// (BetaServerToolCaller value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaDirect, System::Action betaServerTool @@ -257,6 +226,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaDirectCaller value) => {...}, + /// (BetaServerToolCaller value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaDirect, System::Func betaServerTool @@ -276,12 +266,36 @@ public T Match( public static implicit operator Caller(BetaServerToolCaller value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of Caller"); } + this.Switch( + (betaDirect) => betaDirect.Validate(), + (betaServerTool) => betaServerTool.Validate() + ); + } + + public virtual bool Equals(Caller? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaServerToolUseBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaServerToolUseBlockParam.cs index 843f772d..39548422 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaServerToolUseBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaServerToolUseBlockParam.cs @@ -16,100 +16,38 @@ public sealed record class BetaServerToolUseBlockParam : ModelBase { public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new System::ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new System::ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } public required IReadOnlyDictionary Input { get { - if (!this._rawData.TryGetValue("input", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input' cannot be null", - new System::ArgumentOutOfRangeException("input", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'input' cannot be null", - new System::ArgumentNullException("input") - ); - } - init - { - this._rawData["input"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "input" ); } + init { ModelBase.Set(this._rawData, "input", value); } } public required ApiEnum Name { get { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "name" ); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -119,21 +57,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -143,12 +72,9 @@ public BetaServerToolUseBlockParamCaller? Caller { get { - if (!this._rawData.TryGetValue("caller", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "caller" ); } init @@ -158,13 +84,11 @@ public BetaServerToolUseBlockParamCaller? Caller return; } - this._rawData["caller"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "caller", value); } } + /// public override void Validate() { _ = this.ID; @@ -188,6 +112,9 @@ public BetaServerToolUseBlockParam() this.Type = JsonSerializer.Deserialize("\"server_tool_use\""); } + public BetaServerToolUseBlockParam(BetaServerToolUseBlockParam betaServerToolUseBlockParam) + : base(betaServerToolUseBlockParam) { } + public BetaServerToolUseBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -203,6 +130,7 @@ public BetaServerToolUseBlockParam(IReadOnlyDictionary rawD } #pragma warning restore CS8618 + /// public static BetaServerToolUseBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -213,6 +141,7 @@ IReadOnlyDictionary rawData class BetaServerToolUseBlockParamFromRaw : IFromRaw { + /// public BetaServerToolUseBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaServerToolUseBlockParam.FromRawUnchecked(rawData); @@ -316,18 +245,68 @@ public BetaServerToolUseBlockParamCaller(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaDirect(out var value)) { + /// // `value` is of type `BetaDirectCaller` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaDirect([NotNullWhen(true)] out BetaDirectCaller? value) { value = this.Value as BetaDirectCaller; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaServerTool(out var value)) { + /// // `value` is of type `BetaServerToolCaller` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaServerTool([NotNullWhen(true)] out BetaServerToolCaller? value) { value = this.Value as BetaServerToolCaller; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaDirectCaller value) => {...}, + /// (BetaServerToolCaller value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaDirect, System::Action betaServerTool @@ -348,6 +327,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaDirectCaller value) => {...}, + /// (BetaServerToolCaller value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaDirect, System::Func betaServerTool @@ -369,6 +369,16 @@ public static implicit operator BetaServerToolUseBlockParamCaller(BetaDirectCall public static implicit operator BetaServerToolUseBlockParamCaller(BetaServerToolCaller value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -377,6 +387,20 @@ public void Validate() "Data did not match any variant of BetaServerToolUseBlockParamCaller" ); } + this.Switch( + (betaDirect) => betaDirect.Validate(), + (betaServerTool) => betaServerTool.Validate() + ); + } + + public virtual bool Equals(BetaServerToolUseBlockParamCaller? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaSignatureDelta.cs b/src/Anthropic/Models/Beta/Messages/BetaSignatureDelta.cs index 7d41f90a..47a301bb 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaSignatureDelta.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaSignatureDelta.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaSignatureDelta : ModelBase { public required string Signature { - get - { - if (!this._rawData.TryGetValue("signature", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'signature' cannot be null", - new ArgumentOutOfRangeException("signature", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'signature' cannot be null", - new ArgumentNullException("signature") - ); - } - init - { - this._rawData["signature"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "signature"); } + init { ModelBase.Set(this._rawData, "signature", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Signature; @@ -77,6 +43,9 @@ public BetaSignatureDelta() this.Type = JsonSerializer.Deserialize("\"signature_delta\""); } + public BetaSignatureDelta(BetaSignatureDelta betaSignatureDelta) + : base(betaSignatureDelta) { } + public BetaSignatureDelta(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaSignatureDelta(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaSignatureDelta FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public BetaSignatureDelta(string signature) class BetaSignatureDeltaFromRaw : IFromRaw { + /// public BetaSignatureDelta FromRawUnchecked(IReadOnlyDictionary rawData) => BetaSignatureDelta.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaSkill.cs b/src/Anthropic/Models/Beta/Messages/BetaSkill.cs index a64fc4d0..2f14031c 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaSkill.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaSkill.cs @@ -20,27 +20,8 @@ public sealed record class BetaSkill : ModelBase /// public required string SkillID { - get - { - if (!this._rawData.TryGetValue("skill_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'skill_id' cannot be null", - new System::ArgumentOutOfRangeException("skill_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'skill_id' cannot be null", - new System::ArgumentNullException("skill_id") - ); - } - init - { - this._rawData["skill_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "skill_id"); } + init { ModelBase.Set(this._rawData, "skill_id", value); } } /// @@ -50,23 +31,11 @@ public required string SkillID { get { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize< + return ModelBase.GetNotNullClass< ApiEnum - >(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + >(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -74,29 +43,11 @@ public required string SkillID /// public required string Version { - get - { - if (!this._rawData.TryGetValue("version", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'version' cannot be null", - new System::ArgumentOutOfRangeException("version", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'version' cannot be null", - new System::ArgumentNullException("version") - ); - } - init - { - this._rawData["version"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "version"); } + init { ModelBase.Set(this._rawData, "version", value); } } + /// public override void Validate() { _ = this.SkillID; @@ -106,6 +57,9 @@ public override void Validate() public BetaSkill() { } + public BetaSkill(BetaSkill betaSkill) + : base(betaSkill) { } + public BetaSkill(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -119,6 +73,7 @@ public BetaSkill(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaSkill FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -127,6 +82,7 @@ public static BetaSkill FromRawUnchecked(IReadOnlyDictionary { + /// public BetaSkill FromRawUnchecked(IReadOnlyDictionary rawData) => BetaSkill.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaSkillParams.cs b/src/Anthropic/Models/Beta/Messages/BetaSkillParams.cs index 38e43479..48b94fac 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaSkillParams.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaSkillParams.cs @@ -20,27 +20,8 @@ public sealed record class BetaSkillParams : ModelBase /// public required string SkillID { - get - { - if (!this._rawData.TryGetValue("skill_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'skill_id' cannot be null", - new System::ArgumentOutOfRangeException("skill_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'skill_id' cannot be null", - new System::ArgumentNullException("skill_id") - ); - } - init - { - this._rawData["skill_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "skill_id"); } + init { ModelBase.Set(this._rawData, "skill_id", value); } } /// @@ -50,24 +31,12 @@ public required ApiEnum Type { get { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "type" ); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -75,13 +44,7 @@ public required ApiEnum Type /// public string? Version { - get - { - if (!this._rawData.TryGetValue("version", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawData, "version"); } init { if (value == null) @@ -89,13 +52,11 @@ public string? Version return; } - this._rawData["version"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "version", value); } } + /// public override void Validate() { _ = this.SkillID; @@ -105,6 +66,9 @@ public override void Validate() public BetaSkillParams() { } + public BetaSkillParams(BetaSkillParams betaSkillParams) + : base(betaSkillParams) { } + public BetaSkillParams(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -118,6 +82,7 @@ public BetaSkillParams(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaSkillParams FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -126,6 +91,7 @@ public static BetaSkillParams FromRawUnchecked(IReadOnlyDictionary { + /// public BetaSkillParams FromRawUnchecked(IReadOnlyDictionary rawData) => BetaSkillParams.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaTextBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaTextBlock.cs index 367f14ce..6633ea9d 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTextBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTextBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -23,69 +22,24 @@ public required IReadOnlyList? Citations { get { - if (!this._rawData.TryGetValue("citations", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["citations"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass>(this.RawData, "citations"); } + init { ModelBase.Set(this._rawData, "citations", value); } } public required string Text { - get - { - if (!this._rawData.TryGetValue("text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'text' cannot be null", - new ArgumentOutOfRangeException("text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'text' cannot be null", - new ArgumentNullException("text") - ); - } - init - { - this._rawData["text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "text"); } + init { ModelBase.Set(this._rawData, "text", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { foreach (var item in this.Citations ?? []) @@ -104,6 +58,9 @@ public BetaTextBlock() this.Type = JsonSerializer.Deserialize("\"text\""); } + public BetaTextBlock(BetaTextBlock betaTextBlock) + : base(betaTextBlock) { } + public BetaTextBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -119,6 +76,7 @@ public BetaTextBlock(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaTextBlock FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -127,6 +85,7 @@ public static BetaTextBlock FromRawUnchecked(IReadOnlyDictionary { + /// public BetaTextBlock FromRawUnchecked(IReadOnlyDictionary rawData) => BetaTextBlock.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaTextBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaTextBlockParam.cs index b077a3fc..62ef4811 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTextBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTextBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,48 +13,14 @@ public sealed record class BetaTextBlockParam : ModelBase { public required string Text { - get - { - if (!this._rawData.TryGetValue("text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'text' cannot be null", - new ArgumentOutOfRangeException("text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'text' cannot be null", - new ArgumentNullException("text") - ); - } - init - { - this._rawData["text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "text"); } + init { ModelBase.Set(this._rawData, "text", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -65,44 +30,27 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } public IReadOnlyList? Citations { get { - if (!this._rawData.TryGetValue("citations", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["citations"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawData, + "citations" ); } + init { ModelBase.Set(this._rawData, "citations", value); } } + /// public override void Validate() { _ = this.Text; @@ -122,6 +70,9 @@ public BetaTextBlockParam() this.Type = JsonSerializer.Deserialize("\"text\""); } + public BetaTextBlockParam(BetaTextBlockParam betaTextBlockParam) + : base(betaTextBlockParam) { } + public BetaTextBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -137,6 +88,7 @@ public BetaTextBlockParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaTextBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -154,6 +106,7 @@ public BetaTextBlockParam(string text) class BetaTextBlockParamFromRaw : IFromRaw { + /// public BetaTextBlockParam FromRawUnchecked(IReadOnlyDictionary rawData) => BetaTextBlockParam.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaTextCitation.cs b/src/Anthropic/Models/Beta/Messages/BetaTextCitation.cs index c309c7a7..6ed257fd 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTextCitation.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTextCitation.cs @@ -165,18 +165,63 @@ public BetaTextCitation(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationCharLocation(out var value)) { + /// // `value` is of type `BetaCitationCharLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationCharLocation([NotNullWhen(true)] out BetaCitationCharLocation? value) { value = this.Value as BetaCitationCharLocation; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationPageLocation(out var value)) { + /// // `value` is of type `BetaCitationPageLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationPageLocation([NotNullWhen(true)] out BetaCitationPageLocation? value) { value = this.Value as BetaCitationPageLocation; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationContentBlockLocation(out var value)) { + /// // `value` is of type `BetaCitationContentBlockLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationContentBlockLocation( [NotNullWhen(true)] out BetaCitationContentBlockLocation? value ) @@ -185,6 +230,21 @@ public bool TryPickCitationContentBlockLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationsWebSearchResultLocation(out var value)) { + /// // `value` is of type `BetaCitationsWebSearchResultLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationsWebSearchResultLocation( [NotNullWhen(true)] out BetaCitationsWebSearchResultLocation? value ) @@ -193,6 +253,21 @@ public bool TryPickCitationsWebSearchResultLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationSearchResultLocation(out var value)) { + /// // `value` is of type `BetaCitationSearchResultLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationSearchResultLocation( [NotNullWhen(true)] out BetaCitationSearchResultLocation? value ) @@ -201,6 +276,29 @@ public bool TryPickCitationSearchResultLocation( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaCitationCharLocation value) => {...}, + /// (BetaCitationPageLocation value) => {...}, + /// (BetaCitationContentBlockLocation value) => {...}, + /// (BetaCitationsWebSearchResultLocation value) => {...}, + /// (BetaCitationSearchResultLocation value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action citationCharLocation, System::Action citationPageLocation, @@ -233,6 +331,30 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaCitationCharLocation value) => {...}, + /// (BetaCitationPageLocation value) => {...}, + /// (BetaCitationContentBlockLocation value) => {...}, + /// (BetaCitationsWebSearchResultLocation value) => {...}, + /// (BetaCitationSearchResultLocation value) => {...} + /// ); + /// + /// + /// public T Match( System::Func citationCharLocation, System::Func citationPageLocation, @@ -267,6 +389,16 @@ public static implicit operator BetaTextCitation(BetaCitationsWebSearchResultLoc public static implicit operator BetaTextCitation(BetaCitationSearchResultLocation value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -275,6 +407,23 @@ public void Validate() "Data did not match any variant of BetaTextCitation" ); } + this.Switch( + (citationCharLocation) => citationCharLocation.Validate(), + (citationPageLocation) => citationPageLocation.Validate(), + (citationContentBlockLocation) => citationContentBlockLocation.Validate(), + (citationsWebSearchResultLocation) => citationsWebSearchResultLocation.Validate(), + (citationSearchResultLocation) => citationSearchResultLocation.Validate() + ); + } + + public virtual bool Equals(BetaTextCitation? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaTextCitationParam.cs b/src/Anthropic/Models/Beta/Messages/BetaTextCitationParam.cs index 8f2cf0a6..52ac843a 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTextCitationParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTextCitationParam.cs @@ -160,6 +160,21 @@ public BetaTextCitationParam(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationCharLocation(out var value)) { + /// // `value` is of type `BetaCitationCharLocationParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationCharLocation( [NotNullWhen(true)] out BetaCitationCharLocationParam? value ) @@ -168,6 +183,21 @@ public bool TryPickCitationCharLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationPageLocation(out var value)) { + /// // `value` is of type `BetaCitationPageLocationParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationPageLocation( [NotNullWhen(true)] out BetaCitationPageLocationParam? value ) @@ -176,6 +206,21 @@ public bool TryPickCitationPageLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationContentBlockLocation(out var value)) { + /// // `value` is of type `BetaCitationContentBlockLocationParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationContentBlockLocation( [NotNullWhen(true)] out BetaCitationContentBlockLocationParam? value ) @@ -184,6 +229,21 @@ public bool TryPickCitationContentBlockLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationWebSearchResultLocation(out var value)) { + /// // `value` is of type `BetaCitationWebSearchResultLocationParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationWebSearchResultLocation( [NotNullWhen(true)] out BetaCitationWebSearchResultLocationParam? value ) @@ -192,6 +252,21 @@ public bool TryPickCitationWebSearchResultLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationSearchResultLocation(out var value)) { + /// // `value` is of type `BetaCitationSearchResultLocationParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationSearchResultLocation( [NotNullWhen(true)] out BetaCitationSearchResultLocationParam? value ) @@ -200,6 +275,29 @@ public bool TryPickCitationSearchResultLocation( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaCitationCharLocationParam value) => {...}, + /// (BetaCitationPageLocationParam value) => {...}, + /// (BetaCitationContentBlockLocationParam value) => {...}, + /// (BetaCitationWebSearchResultLocationParam value) => {...}, + /// (BetaCitationSearchResultLocationParam value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action citationCharLocation, System::Action citationPageLocation, @@ -232,6 +330,30 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaCitationCharLocationParam value) => {...}, + /// (BetaCitationPageLocationParam value) => {...}, + /// (BetaCitationContentBlockLocationParam value) => {...}, + /// (BetaCitationWebSearchResultLocationParam value) => {...}, + /// (BetaCitationSearchResultLocationParam value) => {...} + /// ); + /// + /// + /// public T Match( System::Func citationCharLocation, System::Func citationPageLocation, @@ -273,6 +395,16 @@ public static implicit operator BetaTextCitationParam( BetaCitationSearchResultLocationParam value ) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -281,6 +413,23 @@ public void Validate() "Data did not match any variant of BetaTextCitationParam" ); } + this.Switch( + (citationCharLocation) => citationCharLocation.Validate(), + (citationPageLocation) => citationPageLocation.Validate(), + (citationContentBlockLocation) => citationContentBlockLocation.Validate(), + (citationWebSearchResultLocation) => citationWebSearchResultLocation.Validate(), + (citationSearchResultLocation) => citationSearchResultLocation.Validate() + ); + } + + public virtual bool Equals(BetaTextCitationParam? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaTextDelta.cs b/src/Anthropic/Models/Beta/Messages/BetaTextDelta.cs index 02d76d68..a11cc882 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTextDelta.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTextDelta.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaTextDelta : ModelBase { public required string Text { - get - { - if (!this._rawData.TryGetValue("text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'text' cannot be null", - new ArgumentOutOfRangeException("text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'text' cannot be null", - new ArgumentNullException("text") - ); - } - init - { - this._rawData["text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "text"); } + init { ModelBase.Set(this._rawData, "text", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Text; @@ -77,6 +43,9 @@ public BetaTextDelta() this.Type = JsonSerializer.Deserialize("\"text_delta\""); } + public BetaTextDelta(BetaTextDelta betaTextDelta) + : base(betaTextDelta) { } + public BetaTextDelta(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaTextDelta(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaTextDelta FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -107,6 +77,7 @@ public BetaTextDelta(string text) class BetaTextDeltaFromRaw : IFromRaw { + /// public BetaTextDelta FromRawUnchecked(IReadOnlyDictionary rawData) => BetaTextDelta.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionCreateResultBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionCreateResultBlock.cs index 42902957..f02226eb 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionCreateResultBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionCreateResultBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,46 +18,17 @@ public sealed record class BetaTextEditorCodeExecutionCreateResultBlock : ModelB { public required bool IsFileUpdate { - get - { - if (!this._rawData.TryGetValue("is_file_update", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'is_file_update' cannot be null", - new ArgumentOutOfRangeException("is_file_update", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["is_file_update"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "is_file_update"); } + init { ModelBase.Set(this._rawData, "is_file_update", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.IsFileUpdate; @@ -82,6 +52,11 @@ public BetaTextEditorCodeExecutionCreateResultBlock() ); } + public BetaTextEditorCodeExecutionCreateResultBlock( + BetaTextEditorCodeExecutionCreateResultBlock betaTextEditorCodeExecutionCreateResultBlock + ) + : base(betaTextEditorCodeExecutionCreateResultBlock) { } + public BetaTextEditorCodeExecutionCreateResultBlock( IReadOnlyDictionary rawData ) @@ -101,6 +76,7 @@ IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaTextEditorCodeExecutionCreateResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -119,6 +95,7 @@ public BetaTextEditorCodeExecutionCreateResultBlock(bool isFileUpdate) class BetaTextEditorCodeExecutionCreateResultBlockFromRaw : IFromRaw { + /// public BetaTextEditorCodeExecutionCreateResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaTextEditorCodeExecutionCreateResultBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionCreateResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionCreateResultBlockParam.cs index 80213512..ae9f72f7 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionCreateResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionCreateResultBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,46 +18,17 @@ public sealed record class BetaTextEditorCodeExecutionCreateResultBlockParam : M { public required bool IsFileUpdate { - get - { - if (!this._rawData.TryGetValue("is_file_update", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'is_file_update' cannot be null", - new ArgumentOutOfRangeException("is_file_update", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["is_file_update"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "is_file_update"); } + init { ModelBase.Set(this._rawData, "is_file_update", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.IsFileUpdate; @@ -82,6 +52,11 @@ public BetaTextEditorCodeExecutionCreateResultBlockParam() ); } + public BetaTextEditorCodeExecutionCreateResultBlockParam( + BetaTextEditorCodeExecutionCreateResultBlockParam betaTextEditorCodeExecutionCreateResultBlockParam + ) + : base(betaTextEditorCodeExecutionCreateResultBlockParam) { } + public BetaTextEditorCodeExecutionCreateResultBlockParam( IReadOnlyDictionary rawData ) @@ -101,6 +76,7 @@ IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaTextEditorCodeExecutionCreateResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -119,6 +95,7 @@ public BetaTextEditorCodeExecutionCreateResultBlockParam(bool isFileUpdate) class BetaTextEditorCodeExecutionCreateResultBlockParamFromRaw : IFromRaw { + /// public BetaTextEditorCodeExecutionCreateResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaTextEditorCodeExecutionCreateResultBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionStrReplaceResultBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionStrReplaceResultBlock.cs index 2175c47e..7274dc09 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionStrReplaceResultBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionStrReplaceResultBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,115 +18,41 @@ public sealed record class BetaTextEditorCodeExecutionStrReplaceResultBlock : Mo { public required IReadOnlyList? Lines { - get - { - if (!this._rawData.TryGetValue("lines", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["lines"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "lines"); } + init { ModelBase.Set(this._rawData, "lines", value); } } public required long? NewLines { - get - { - if (!this._rawData.TryGetValue("new_lines", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["new_lines"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "new_lines"); } + init { ModelBase.Set(this._rawData, "new_lines", value); } } public required long? NewStart { - get - { - if (!this._rawData.TryGetValue("new_start", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["new_start"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "new_start"); } + init { ModelBase.Set(this._rawData, "new_start", value); } } public required long? OldLines { - get - { - if (!this._rawData.TryGetValue("old_lines", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["old_lines"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "old_lines"); } + init { ModelBase.Set(this._rawData, "old_lines", value); } } public required long? OldStart { - get - { - if (!this._rawData.TryGetValue("old_start", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["old_start"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "old_start"); } + init { ModelBase.Set(this._rawData, "old_start", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Lines; @@ -155,6 +80,11 @@ public BetaTextEditorCodeExecutionStrReplaceResultBlock() ); } + public BetaTextEditorCodeExecutionStrReplaceResultBlock( + BetaTextEditorCodeExecutionStrReplaceResultBlock betaTextEditorCodeExecutionStrReplaceResultBlock + ) + : base(betaTextEditorCodeExecutionStrReplaceResultBlock) { } + public BetaTextEditorCodeExecutionStrReplaceResultBlock( IReadOnlyDictionary rawData ) @@ -174,6 +104,7 @@ IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaTextEditorCodeExecutionStrReplaceResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -185,6 +116,7 @@ IReadOnlyDictionary rawData class BetaTextEditorCodeExecutionStrReplaceResultBlockFromRaw : IFromRaw { + /// public BetaTextEditorCodeExecutionStrReplaceResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaTextEditorCodeExecutionStrReplaceResultBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionStrReplaceResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionStrReplaceResultBlockParam.cs index 7e0484a2..63b5bb92 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionStrReplaceResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionStrReplaceResultBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,115 +18,41 @@ public sealed record class BetaTextEditorCodeExecutionStrReplaceResultBlockParam { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public IReadOnlyList? Lines { - get - { - if (!this._rawData.TryGetValue("lines", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["lines"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "lines"); } + init { ModelBase.Set(this._rawData, "lines", value); } } public long? NewLines { - get - { - if (!this._rawData.TryGetValue("new_lines", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["new_lines"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "new_lines"); } + init { ModelBase.Set(this._rawData, "new_lines", value); } } public long? NewStart { - get - { - if (!this._rawData.TryGetValue("new_start", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["new_start"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "new_start"); } + init { ModelBase.Set(this._rawData, "new_start", value); } } public long? OldLines { - get - { - if (!this._rawData.TryGetValue("old_lines", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["old_lines"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "old_lines"); } + init { ModelBase.Set(this._rawData, "old_lines", value); } } public long? OldStart { - get - { - if (!this._rawData.TryGetValue("old_start", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["old_start"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "old_start"); } + init { ModelBase.Set(this._rawData, "old_start", value); } } + /// public override void Validate() { if ( @@ -155,6 +80,11 @@ public BetaTextEditorCodeExecutionStrReplaceResultBlockParam() ); } + public BetaTextEditorCodeExecutionStrReplaceResultBlockParam( + BetaTextEditorCodeExecutionStrReplaceResultBlockParam betaTextEditorCodeExecutionStrReplaceResultBlockParam + ) + : base(betaTextEditorCodeExecutionStrReplaceResultBlockParam) { } + public BetaTextEditorCodeExecutionStrReplaceResultBlockParam( IReadOnlyDictionary rawData ) @@ -176,6 +106,7 @@ FrozenDictionary rawData } #pragma warning restore CS8618 + /// public static BetaTextEditorCodeExecutionStrReplaceResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -187,6 +118,7 @@ IReadOnlyDictionary rawData class BetaTextEditorCodeExecutionStrReplaceResultBlockParamFromRaw : IFromRaw { + /// public BetaTextEditorCodeExecutionStrReplaceResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaTextEditorCodeExecutionStrReplaceResultBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultBlock.cs index 496df34e..1fa5f95b 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultBlock.cs @@ -21,79 +21,27 @@ public required BetaTextEditorCodeExecutionToolResultBlockContent Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentOutOfRangeException( - "tool_use_id", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -118,6 +66,11 @@ public BetaTextEditorCodeExecutionToolResultBlock() ); } + public BetaTextEditorCodeExecutionToolResultBlock( + BetaTextEditorCodeExecutionToolResultBlock betaTextEditorCodeExecutionToolResultBlock + ) + : base(betaTextEditorCodeExecutionToolResultBlock) { } + public BetaTextEditorCodeExecutionToolResultBlock( IReadOnlyDictionary rawData ) @@ -137,6 +90,7 @@ IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaTextEditorCodeExecutionToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -148,6 +102,7 @@ IReadOnlyDictionary rawData class BetaTextEditorCodeExecutionToolResultBlockFromRaw : IFromRaw { + /// public BetaTextEditorCodeExecutionToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaTextEditorCodeExecutionToolResultBlock.FromRawUnchecked(rawData); @@ -219,6 +174,21 @@ public BetaTextEditorCodeExecutionToolResultBlockContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaTextEditorCodeExecutionToolResultError(out var value)) { + /// // `value` is of type `BetaTextEditorCodeExecutionToolResultError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaTextEditorCodeExecutionToolResultError( [NotNullWhen(true)] out BetaTextEditorCodeExecutionToolResultError? value ) @@ -227,6 +197,21 @@ public bool TryPickBetaTextEditorCodeExecutionToolResultError( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaTextEditorCodeExecutionViewResultBlock(out var value)) { + /// // `value` is of type `BetaTextEditorCodeExecutionViewResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaTextEditorCodeExecutionViewResultBlock( [NotNullWhen(true)] out BetaTextEditorCodeExecutionViewResultBlock? value ) @@ -235,6 +220,21 @@ public bool TryPickBetaTextEditorCodeExecutionViewResultBlock( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaTextEditorCodeExecutionCreateResultBlock(out var value)) { + /// // `value` is of type `BetaTextEditorCodeExecutionCreateResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaTextEditorCodeExecutionCreateResultBlock( [NotNullWhen(true)] out BetaTextEditorCodeExecutionCreateResultBlock? value ) @@ -243,6 +243,21 @@ public bool TryPickBetaTextEditorCodeExecutionCreateResultBlock( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaTextEditorCodeExecutionStrReplaceResultBlock(out var value)) { + /// // `value` is of type `BetaTextEditorCodeExecutionStrReplaceResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaTextEditorCodeExecutionStrReplaceResultBlock( [NotNullWhen(true)] out BetaTextEditorCodeExecutionStrReplaceResultBlock? value ) @@ -251,6 +266,28 @@ public bool TryPickBetaTextEditorCodeExecutionStrReplaceResultBlock( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaTextEditorCodeExecutionToolResultError value) => {...}, + /// (BetaTextEditorCodeExecutionViewResultBlock value) => {...}, + /// (BetaTextEditorCodeExecutionCreateResultBlock value) => {...}, + /// (BetaTextEditorCodeExecutionStrReplaceResultBlock value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaTextEditorCodeExecutionToolResultError, System::Action betaTextEditorCodeExecutionViewResultBlock, @@ -279,6 +316,29 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaTextEditorCodeExecutionToolResultError value) => {...}, + /// (BetaTextEditorCodeExecutionViewResultBlock value) => {...}, + /// (BetaTextEditorCodeExecutionCreateResultBlock value) => {...}, + /// (BetaTextEditorCodeExecutionStrReplaceResultBlock value) => {...} + /// ); + /// + /// + /// public T Match( System::Func< BetaTextEditorCodeExecutionToolResultError, @@ -330,6 +390,16 @@ public static implicit operator BetaTextEditorCodeExecutionToolResultBlockConten BetaTextEditorCodeExecutionStrReplaceResultBlock value ) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -338,6 +408,26 @@ public void Validate() "Data did not match any variant of BetaTextEditorCodeExecutionToolResultBlockContent" ); } + this.Switch( + (betaTextEditorCodeExecutionToolResultError) => + betaTextEditorCodeExecutionToolResultError.Validate(), + (betaTextEditorCodeExecutionViewResultBlock) => + betaTextEditorCodeExecutionViewResultBlock.Validate(), + (betaTextEditorCodeExecutionCreateResultBlock) => + betaTextEditorCodeExecutionCreateResultBlock.Validate(), + (betaTextEditorCodeExecutionStrReplaceResultBlock) => + betaTextEditorCodeExecutionStrReplaceResultBlock.Validate() + ); + } + + public virtual bool Equals(BetaTextEditorCodeExecutionToolResultBlockContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultBlockParam.cs index fa1dd76f..b93b87f6 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultBlockParam.cs @@ -21,77 +21,24 @@ public required BetaTextEditorCodeExecutionToolResultBlockParamContent Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentOutOfRangeException( - "tool_use_id", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -101,23 +48,15 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -143,6 +82,11 @@ public BetaTextEditorCodeExecutionToolResultBlockParam() ); } + public BetaTextEditorCodeExecutionToolResultBlockParam( + BetaTextEditorCodeExecutionToolResultBlockParam betaTextEditorCodeExecutionToolResultBlockParam + ) + : base(betaTextEditorCodeExecutionToolResultBlockParam) { } + public BetaTextEditorCodeExecutionToolResultBlockParam( IReadOnlyDictionary rawData ) @@ -162,6 +106,7 @@ IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaTextEditorCodeExecutionToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -173,6 +118,7 @@ IReadOnlyDictionary rawData class BetaTextEditorCodeExecutionToolResultBlockParamFromRaw : IFromRaw { + /// public BetaTextEditorCodeExecutionToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaTextEditorCodeExecutionToolResultBlockParam.FromRawUnchecked(rawData); @@ -244,6 +190,21 @@ public BetaTextEditorCodeExecutionToolResultBlockParamContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaTextEditorCodeExecutionToolResultErrorParam(out var value)) { + /// // `value` is of type `BetaTextEditorCodeExecutionToolResultErrorParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaTextEditorCodeExecutionToolResultErrorParam( [NotNullWhen(true)] out BetaTextEditorCodeExecutionToolResultErrorParam? value ) @@ -252,6 +213,21 @@ public bool TryPickBetaTextEditorCodeExecutionToolResultErrorParam( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaTextEditorCodeExecutionViewResultBlockParam(out var value)) { + /// // `value` is of type `BetaTextEditorCodeExecutionViewResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaTextEditorCodeExecutionViewResultBlockParam( [NotNullWhen(true)] out BetaTextEditorCodeExecutionViewResultBlockParam? value ) @@ -260,6 +236,21 @@ public bool TryPickBetaTextEditorCodeExecutionViewResultBlockParam( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaTextEditorCodeExecutionCreateResultBlockParam(out var value)) { + /// // `value` is of type `BetaTextEditorCodeExecutionCreateResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaTextEditorCodeExecutionCreateResultBlockParam( [NotNullWhen(true)] out BetaTextEditorCodeExecutionCreateResultBlockParam? value ) @@ -268,6 +259,21 @@ public bool TryPickBetaTextEditorCodeExecutionCreateResultBlockParam( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaTextEditorCodeExecutionStrReplaceResultBlockParam(out var value)) { + /// // `value` is of type `BetaTextEditorCodeExecutionStrReplaceResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaTextEditorCodeExecutionStrReplaceResultBlockParam( [NotNullWhen(true)] out BetaTextEditorCodeExecutionStrReplaceResultBlockParam? value ) @@ -276,6 +282,28 @@ public bool TryPickBetaTextEditorCodeExecutionStrReplaceResultBlockParam( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaTextEditorCodeExecutionToolResultErrorParam value) => {...}, + /// (BetaTextEditorCodeExecutionViewResultBlockParam value) => {...}, + /// (BetaTextEditorCodeExecutionCreateResultBlockParam value) => {...}, + /// (BetaTextEditorCodeExecutionStrReplaceResultBlockParam value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaTextEditorCodeExecutionToolResultErrorParam, System::Action betaTextEditorCodeExecutionViewResultBlockParam, @@ -304,6 +332,29 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaTextEditorCodeExecutionToolResultErrorParam value) => {...}, + /// (BetaTextEditorCodeExecutionViewResultBlockParam value) => {...}, + /// (BetaTextEditorCodeExecutionCreateResultBlockParam value) => {...}, + /// (BetaTextEditorCodeExecutionStrReplaceResultBlockParam value) => {...} + /// ); + /// + /// + /// public T Match( System::Func< BetaTextEditorCodeExecutionToolResultErrorParam, @@ -355,6 +406,16 @@ public static implicit operator BetaTextEditorCodeExecutionToolResultBlockParamC BetaTextEditorCodeExecutionStrReplaceResultBlockParam value ) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -363,6 +424,26 @@ public void Validate() "Data did not match any variant of BetaTextEditorCodeExecutionToolResultBlockParamContent" ); } + this.Switch( + (betaTextEditorCodeExecutionToolResultErrorParam) => + betaTextEditorCodeExecutionToolResultErrorParam.Validate(), + (betaTextEditorCodeExecutionViewResultBlockParam) => + betaTextEditorCodeExecutionViewResultBlockParam.Validate(), + (betaTextEditorCodeExecutionCreateResultBlockParam) => + betaTextEditorCodeExecutionCreateResultBlockParam.Validate(), + (betaTextEditorCodeExecutionStrReplaceResultBlockParam) => + betaTextEditorCodeExecutionStrReplaceResultBlockParam.Validate() + ); + } + + public virtual bool Equals(BetaTextEditorCodeExecutionToolResultBlockParamContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultError.cs b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultError.cs index ebaa4524..4126ec4f 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultError.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultError.cs @@ -21,67 +21,26 @@ public required ApiEnum - >(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["error_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + >(this.RawData, "error_code"); } + init { ModelBase.Set(this._rawData, "error_code", value); } } public required string? ErrorMessage { - get - { - if (!this._rawData.TryGetValue("error_message", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["error_message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "error_message"); } + init { ModelBase.Set(this._rawData, "error_message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.ErrorCode.Validate(); @@ -106,6 +65,11 @@ public BetaTextEditorCodeExecutionToolResultError() ); } + public BetaTextEditorCodeExecutionToolResultError( + BetaTextEditorCodeExecutionToolResultError betaTextEditorCodeExecutionToolResultError + ) + : base(betaTextEditorCodeExecutionToolResultError) { } + public BetaTextEditorCodeExecutionToolResultError( IReadOnlyDictionary rawData ) @@ -125,6 +89,7 @@ IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaTextEditorCodeExecutionToolResultError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -136,6 +101,7 @@ IReadOnlyDictionary rawData class BetaTextEditorCodeExecutionToolResultErrorFromRaw : IFromRaw { + /// public BetaTextEditorCodeExecutionToolResultError FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaTextEditorCodeExecutionToolResultError.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultErrorParam.cs b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultErrorParam.cs index 40daea99..6e290b5e 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultErrorParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionToolResultErrorParam.cs @@ -24,67 +24,26 @@ public required ApiEnum< { get { - if (!this._rawData.TryGetValue("error_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error_code' cannot be null", - new System::ArgumentOutOfRangeException( - "error_code", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize< + return ModelBase.GetNotNullClass< ApiEnum - >(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["error_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + >(this.RawData, "error_code"); } + init { ModelBase.Set(this._rawData, "error_code", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public string? ErrorMessage { - get - { - if (!this._rawData.TryGetValue("error_message", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["error_message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "error_message"); } + init { ModelBase.Set(this._rawData, "error_message", value); } } + /// public override void Validate() { this.ErrorCode.Validate(); @@ -109,6 +68,11 @@ public BetaTextEditorCodeExecutionToolResultErrorParam() ); } + public BetaTextEditorCodeExecutionToolResultErrorParam( + BetaTextEditorCodeExecutionToolResultErrorParam betaTextEditorCodeExecutionToolResultErrorParam + ) + : base(betaTextEditorCodeExecutionToolResultErrorParam) { } + public BetaTextEditorCodeExecutionToolResultErrorParam( IReadOnlyDictionary rawData ) @@ -128,6 +92,7 @@ IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaTextEditorCodeExecutionToolResultErrorParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -148,6 +113,7 @@ ApiEnum errorC class BetaTextEditorCodeExecutionToolResultErrorParamFromRaw : IFromRaw { + /// public BetaTextEditorCodeExecutionToolResultErrorParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaTextEditorCodeExecutionToolResultErrorParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionViewResultBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionViewResultBlock.cs index f24de408..012790be 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionViewResultBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionViewResultBlock.cs @@ -19,131 +19,44 @@ public sealed record class BetaTextEditorCodeExecutionViewResultBlock : ModelBas { public required string Content { - get - { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "content"); } + init { ModelBase.Set(this._rawData, "content", value); } } public required ApiEnum FileType { get { - if (!this._rawData.TryGetValue("file_type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'file_type' cannot be null", - new System::ArgumentOutOfRangeException( - "file_type", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["file_type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNotNullClass>(this.RawData, "file_type"); } + init { ModelBase.Set(this._rawData, "file_type", value); } } public required long? NumLines { - get - { - if (!this._rawData.TryGetValue("num_lines", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["num_lines"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "num_lines"); } + init { ModelBase.Set(this._rawData, "num_lines", value); } } public required long? StartLine { - get - { - if (!this._rawData.TryGetValue("start_line", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_line"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "start_line"); } + init { ModelBase.Set(this._rawData, "start_line", value); } } public required long? TotalLines { - get - { - if (!this._rawData.TryGetValue("total_lines", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["total_lines"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "total_lines"); } + init { ModelBase.Set(this._rawData, "total_lines", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Content; @@ -171,6 +84,11 @@ public BetaTextEditorCodeExecutionViewResultBlock() ); } + public BetaTextEditorCodeExecutionViewResultBlock( + BetaTextEditorCodeExecutionViewResultBlock betaTextEditorCodeExecutionViewResultBlock + ) + : base(betaTextEditorCodeExecutionViewResultBlock) { } + public BetaTextEditorCodeExecutionViewResultBlock( IReadOnlyDictionary rawData ) @@ -190,6 +108,7 @@ IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaTextEditorCodeExecutionViewResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -201,6 +120,7 @@ IReadOnlyDictionary rawData class BetaTextEditorCodeExecutionViewResultBlockFromRaw : IFromRaw { + /// public BetaTextEditorCodeExecutionViewResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaTextEditorCodeExecutionViewResultBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionViewResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionViewResultBlockParam.cs index 2eaa02c6..e55daf72 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionViewResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTextEditorCodeExecutionViewResultBlockParam.cs @@ -19,27 +19,8 @@ public sealed record class BetaTextEditorCodeExecutionViewResultBlockParam : Mod { public required string Content { - get - { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "content"); } + init { ModelBase.Set(this._rawData, "content", value); } } public required ApiEnum< @@ -49,103 +30,38 @@ public required ApiEnum< { get { - if (!this._rawData.TryGetValue("file_type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'file_type' cannot be null", - new System::ArgumentOutOfRangeException( - "file_type", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize< + return ModelBase.GetNotNullClass< ApiEnum - >(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["file_type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + >(this.RawData, "file_type"); } + init { ModelBase.Set(this._rawData, "file_type", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public long? NumLines { - get - { - if (!this._rawData.TryGetValue("num_lines", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["num_lines"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "num_lines"); } + init { ModelBase.Set(this._rawData, "num_lines", value); } } public long? StartLine { - get - { - if (!this._rawData.TryGetValue("start_line", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_line"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "start_line"); } + init { ModelBase.Set(this._rawData, "start_line", value); } } public long? TotalLines { - get - { - if (!this._rawData.TryGetValue("total_lines", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["total_lines"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "total_lines"); } + init { ModelBase.Set(this._rawData, "total_lines", value); } } + /// public override void Validate() { _ = this.Content; @@ -173,6 +89,11 @@ public BetaTextEditorCodeExecutionViewResultBlockParam() ); } + public BetaTextEditorCodeExecutionViewResultBlockParam( + BetaTextEditorCodeExecutionViewResultBlockParam betaTextEditorCodeExecutionViewResultBlockParam + ) + : base(betaTextEditorCodeExecutionViewResultBlockParam) { } + public BetaTextEditorCodeExecutionViewResultBlockParam( IReadOnlyDictionary rawData ) @@ -192,6 +113,7 @@ IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaTextEditorCodeExecutionViewResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -203,6 +125,7 @@ IReadOnlyDictionary rawData class BetaTextEditorCodeExecutionViewResultBlockParamFromRaw : IFromRaw { + /// public BetaTextEditorCodeExecutionViewResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaTextEditorCodeExecutionViewResultBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaThinkingBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaThinkingBlock.cs index e560338b..62621c4a 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaThinkingBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaThinkingBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,75 +13,23 @@ public sealed record class BetaThinkingBlock : ModelBase { public required string Signature { - get - { - if (!this._rawData.TryGetValue("signature", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'signature' cannot be null", - new ArgumentOutOfRangeException("signature", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'signature' cannot be null", - new ArgumentNullException("signature") - ); - } - init - { - this._rawData["signature"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "signature"); } + init { ModelBase.Set(this._rawData, "signature", value); } } public required string Thinking { - get - { - if (!this._rawData.TryGetValue("thinking", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'thinking' cannot be null", - new ArgumentOutOfRangeException("thinking", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'thinking' cannot be null", - new ArgumentNullException("thinking") - ); - } - init - { - this._rawData["thinking"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "thinking"); } + init { ModelBase.Set(this._rawData, "thinking", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Signature; @@ -103,6 +50,9 @@ public BetaThinkingBlock() this.Type = JsonSerializer.Deserialize("\"thinking\""); } + public BetaThinkingBlock(BetaThinkingBlock betaThinkingBlock) + : base(betaThinkingBlock) { } + public BetaThinkingBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -118,6 +68,7 @@ public BetaThinkingBlock(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaThinkingBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -128,6 +79,7 @@ IReadOnlyDictionary rawData class BetaThinkingBlockFromRaw : IFromRaw { + /// public BetaThinkingBlock FromRawUnchecked(IReadOnlyDictionary rawData) => BetaThinkingBlock.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaThinkingBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaThinkingBlockParam.cs index 54bc945c..0111e020 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaThinkingBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaThinkingBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,75 +13,23 @@ public sealed record class BetaThinkingBlockParam : ModelBase { public required string Signature { - get - { - if (!this._rawData.TryGetValue("signature", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'signature' cannot be null", - new ArgumentOutOfRangeException("signature", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'signature' cannot be null", - new ArgumentNullException("signature") - ); - } - init - { - this._rawData["signature"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "signature"); } + init { ModelBase.Set(this._rawData, "signature", value); } } public required string Thinking { - get - { - if (!this._rawData.TryGetValue("thinking", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'thinking' cannot be null", - new ArgumentOutOfRangeException("thinking", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'thinking' cannot be null", - new ArgumentNullException("thinking") - ); - } - init - { - this._rawData["thinking"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "thinking"); } + init { ModelBase.Set(this._rawData, "thinking", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Signature; @@ -103,6 +50,9 @@ public BetaThinkingBlockParam() this.Type = JsonSerializer.Deserialize("\"thinking\""); } + public BetaThinkingBlockParam(BetaThinkingBlockParam betaThinkingBlockParam) + : base(betaThinkingBlockParam) { } + public BetaThinkingBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -118,6 +68,7 @@ public BetaThinkingBlockParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaThinkingBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -128,6 +79,7 @@ IReadOnlyDictionary rawData class BetaThinkingBlockParamFromRaw : IFromRaw { + /// public BetaThinkingBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaThinkingBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaThinkingConfigDisabled.cs b/src/Anthropic/Models/Beta/Messages/BetaThinkingConfigDisabled.cs index 421f3dd2..d8a517c5 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaThinkingConfigDisabled.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaThinkingConfigDisabled.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,25 +15,11 @@ public sealed record class BetaThinkingConfigDisabled : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { if ( @@ -53,6 +38,9 @@ public BetaThinkingConfigDisabled() this.Type = JsonSerializer.Deserialize("\"disabled\""); } + public BetaThinkingConfigDisabled(BetaThinkingConfigDisabled betaThinkingConfigDisabled) + : base(betaThinkingConfigDisabled) { } + public BetaThinkingConfigDisabled(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -68,6 +56,7 @@ public BetaThinkingConfigDisabled(IReadOnlyDictionary rawDa } #pragma warning restore CS8618 + /// public static BetaThinkingConfigDisabled FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -78,6 +67,7 @@ IReadOnlyDictionary rawData class BetaThinkingConfigDisabledFromRaw : IFromRaw { + /// public BetaThinkingConfigDisabled FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaThinkingConfigDisabled.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaThinkingConfigEnabled.cs b/src/Anthropic/Models/Beta/Messages/BetaThinkingConfigEnabled.cs index 05e12cf5..f8d316c2 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaThinkingConfigEnabled.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaThinkingConfigEnabled.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -24,46 +23,17 @@ public sealed record class BetaThinkingConfigEnabled : ModelBase /// public required long BudgetTokens { - get - { - if (!this._rawData.TryGetValue("budget_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'budget_tokens' cannot be null", - new ArgumentOutOfRangeException("budget_tokens", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["budget_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "budget_tokens"); } + init { ModelBase.Set(this._rawData, "budget_tokens", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.BudgetTokens; @@ -83,6 +53,9 @@ public BetaThinkingConfigEnabled() this.Type = JsonSerializer.Deserialize("\"enabled\""); } + public BetaThinkingConfigEnabled(BetaThinkingConfigEnabled betaThinkingConfigEnabled) + : base(betaThinkingConfigEnabled) { } + public BetaThinkingConfigEnabled(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -98,6 +71,7 @@ public BetaThinkingConfigEnabled(IReadOnlyDictionary rawDat } #pragma warning restore CS8618 + /// public static BetaThinkingConfigEnabled FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -115,6 +89,7 @@ public BetaThinkingConfigEnabled(long budgetTokens) class BetaThinkingConfigEnabledFromRaw : IFromRaw { + /// public BetaThinkingConfigEnabled FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaThinkingConfigEnabled.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaThinkingConfigParam.cs b/src/Anthropic/Models/Beta/Messages/BetaThinkingConfigParam.cs index 1e05a5a9..b1814873 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaThinkingConfigParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaThinkingConfigParam.cs @@ -50,18 +50,68 @@ public BetaThinkingConfigParam(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickEnabled(out var value)) { + /// // `value` is of type `BetaThinkingConfigEnabled` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickEnabled([NotNullWhen(true)] out BetaThinkingConfigEnabled? value) { value = this.Value as BetaThinkingConfigEnabled; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickDisabled(out var value)) { + /// // `value` is of type `BetaThinkingConfigDisabled` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickDisabled([NotNullWhen(true)] out BetaThinkingConfigDisabled? value) { value = this.Value as BetaThinkingConfigDisabled; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaThinkingConfigEnabled value) => {...}, + /// (BetaThinkingConfigDisabled value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action enabled, System::Action disabled @@ -82,6 +132,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaThinkingConfigEnabled value) => {...}, + /// (BetaThinkingConfigDisabled value) => {...} + /// ); + /// + /// + /// public T Match( System::Func enabled, System::Func disabled @@ -103,6 +174,16 @@ public static implicit operator BetaThinkingConfigParam(BetaThinkingConfigEnable public static implicit operator BetaThinkingConfigParam(BetaThinkingConfigDisabled value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -111,6 +192,17 @@ public void Validate() "Data did not match any variant of BetaThinkingConfigParam" ); } + this.Switch((enabled) => enabled.Validate(), (disabled) => disabled.Validate()); + } + + public virtual bool Equals(BetaThinkingConfigParam? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaThinkingDelta.cs b/src/Anthropic/Models/Beta/Messages/BetaThinkingDelta.cs index 8d7b03c3..33bfbc11 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaThinkingDelta.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaThinkingDelta.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaThinkingDelta : ModelBase { public required string Thinking { - get - { - if (!this._rawData.TryGetValue("thinking", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'thinking' cannot be null", - new ArgumentOutOfRangeException("thinking", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'thinking' cannot be null", - new ArgumentNullException("thinking") - ); - } - init - { - this._rawData["thinking"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "thinking"); } + init { ModelBase.Set(this._rawData, "thinking", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Thinking; @@ -77,6 +43,9 @@ public BetaThinkingDelta() this.Type = JsonSerializer.Deserialize("\"thinking_delta\""); } + public BetaThinkingDelta(BetaThinkingDelta betaThinkingDelta) + : base(betaThinkingDelta) { } + public BetaThinkingDelta(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaThinkingDelta(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaThinkingDelta FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public BetaThinkingDelta(string thinking) class BetaThinkingDeltaFromRaw : IFromRaw { + /// public BetaThinkingDelta FromRawUnchecked(IReadOnlyDictionary rawData) => BetaThinkingDelta.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaThinkingTurns.cs b/src/Anthropic/Models/Beta/Messages/BetaThinkingTurns.cs index e40fde08..6d7573cc 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaThinkingTurns.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaThinkingTurns.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,46 +13,17 @@ public sealed record class BetaThinkingTurns : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required long Value { - get - { - if (!this._rawData.TryGetValue("value", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'value' cannot be null", - new ArgumentOutOfRangeException("value", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["value"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "value"); } + init { ModelBase.Set(this._rawData, "value", value); } } + /// public override void Validate() { if ( @@ -73,6 +43,9 @@ public BetaThinkingTurns() this.Type = JsonSerializer.Deserialize("\"thinking_turns\""); } + public BetaThinkingTurns(BetaThinkingTurns betaThinkingTurns) + : base(betaThinkingTurns) { } + public BetaThinkingTurns(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -88,6 +61,7 @@ public BetaThinkingTurns(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaThinkingTurns FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -105,6 +79,7 @@ public BetaThinkingTurns(long value) class BetaThinkingTurnsFromRaw : IFromRaw { + /// public BetaThinkingTurns FromRawUnchecked(IReadOnlyDictionary rawData) => BetaThinkingTurns.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaTool.cs b/src/Anthropic/Models/Beta/Messages/BetaTool.cs index 4662628a..a7754c25 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaTool.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaTool.cs @@ -20,30 +20,8 @@ public sealed record class BetaTool : ModelBase /// public required InputSchema InputSchema { - get - { - if (!this._rawData.TryGetValue("input_schema", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input_schema' cannot be null", - new System::ArgumentOutOfRangeException( - "input_schema", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'input_schema' cannot be null", - new System::ArgumentNullException("input_schema") - ); - } - init - { - this._rawData["input_schema"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "input_schema"); } + init { ModelBase.Set(this._rawData, "input_schema", value); } } /// @@ -53,39 +31,17 @@ public required InputSchema InputSchema /// public required string Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentNullException("name") - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList>? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawData, + "allowed_callers" ); } init @@ -95,10 +51,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -109,21 +62,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -132,13 +76,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -146,10 +84,7 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } @@ -163,13 +98,7 @@ public bool? DeferLoading /// public string? Description { - get - { - if (!this._rawData.TryGetValue("description", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawData, "description"); } init { if (value == null) @@ -177,10 +106,7 @@ public string? Description return; } - this._rawData["description"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "description", value); } } @@ -188,12 +114,9 @@ public IReadOnlyList>? InputExamples { get { - if (!this._rawData.TryGetValue("input_examples", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawData, + "input_examples" ); } init @@ -203,22 +126,13 @@ public IReadOnlyList>? InputExamples return; } - this._rawData["input_examples"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "input_examples", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -226,10 +140,7 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } @@ -237,23 +148,12 @@ public ApiEnum? Type { get { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass>(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.InputSchema.Validate(); @@ -272,6 +172,9 @@ public override void Validate() public BetaTool() { } + public BetaTool(BetaTool betaTool) + : base(betaTool) { } + public BetaTool(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -285,6 +188,7 @@ public BetaTool(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaTool FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -293,6 +197,7 @@ public static BetaTool FromRawUnchecked(IReadOnlyDictionary class BetaToolFromRaw : IFromRaw { + /// public BetaTool FromRawUnchecked(IReadOnlyDictionary rawData) => BetaTool.FromRawUnchecked(rawData); } @@ -308,64 +213,29 @@ public sealed record class InputSchema : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public IReadOnlyDictionary? Properties { get { - if (!this._rawData.TryGetValue("properties", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["properties"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawData, + "properties" ); } + init { ModelBase.Set(this._rawData, "properties", value); } } public IReadOnlyList? Required { - get - { - if (!this._rawData.TryGetValue("required", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["required"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "required"); } + init { ModelBase.Set(this._rawData, "required", value); } } + /// public override void Validate() { if ( @@ -386,6 +256,9 @@ public InputSchema() this.Type = JsonSerializer.Deserialize("\"object\""); } + public InputSchema(InputSchema inputSchema) + : base(inputSchema) { } + public InputSchema(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -401,6 +274,7 @@ public InputSchema(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static InputSchema FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -409,20 +283,21 @@ public static InputSchema FromRawUnchecked(IReadOnlyDictionary { + /// public InputSchema FromRawUnchecked(IReadOnlyDictionary rawData) => InputSchema.FromRawUnchecked(rawData); } -[JsonConverter(typeof(AllowedCaller2Converter))] -public enum AllowedCaller2 +[JsonConverter(typeof(BetaToolAllowedCallerConverter))] +public enum BetaToolAllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCaller2Converter : JsonConverter +sealed class BetaToolAllowedCallerConverter : JsonConverter { - public override AllowedCaller2 Read( + public override BetaToolAllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -430,15 +305,15 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCaller2.Direct, - "code_execution_20250825" => AllowedCaller2.CodeExecution20250825, - _ => (AllowedCaller2)(-1), + "direct" => BetaToolAllowedCaller.Direct, + "code_execution_20250825" => BetaToolAllowedCaller.CodeExecution20250825, + _ => (BetaToolAllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCaller2 value, + BetaToolAllowedCaller value, JsonSerializerOptions options ) { @@ -446,8 +321,8 @@ JsonSerializerOptions options writer, value switch { - AllowedCaller2.Direct => "direct", - AllowedCaller2.CodeExecution20250825 => "code_execution_20250825", + BetaToolAllowedCaller.Direct => "direct", + BetaToolAllowedCaller.CodeExecution20250825 => "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolBash20241022.cs b/src/Anthropic/Models/Beta/Messages/BetaToolBash20241022.cs index 2ba60202..acaf8843 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolBash20241022.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolBash20241022.cs @@ -19,57 +19,23 @@ public sealed record class BetaToolBash20241022 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList>? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + List> + >(this.RawData, "allowed_callers"); } init { @@ -78,10 +44,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -92,21 +55,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -115,13 +69,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -129,10 +77,7 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } @@ -140,12 +85,9 @@ public IReadOnlyList>? InputExamples { get { - if (!this._rawData.TryGetValue("input_examples", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawData, + "input_examples" ); } init @@ -155,22 +97,13 @@ public IReadOnlyList>? InputExamples return; } - this._rawData["input_examples"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "input_examples", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -178,13 +111,11 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } + /// public override void Validate() { if (!JsonElement.DeepEquals(this.Name, JsonSerializer.Deserialize("\"bash\""))) @@ -216,6 +147,9 @@ public BetaToolBash20241022() this.Type = JsonSerializer.Deserialize("\"bash_20241022\""); } + public BetaToolBash20241022(BetaToolBash20241022 betaToolBash20241022) + : base(betaToolBash20241022) { } + public BetaToolBash20241022(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -232,6 +166,7 @@ public BetaToolBash20241022(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaToolBash20241022 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -242,21 +177,23 @@ IReadOnlyDictionary rawData class BetaToolBash20241022FromRaw : IFromRaw { + /// public BetaToolBash20241022 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolBash20241022.FromRawUnchecked(rawData); } -[JsonConverter(typeof(AllowedCaller3Converter))] -public enum AllowedCaller3 +[JsonConverter(typeof(BetaToolBash20241022AllowedCallerConverter))] +public enum BetaToolBash20241022AllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCaller3Converter : JsonConverter +sealed class BetaToolBash20241022AllowedCallerConverter + : JsonConverter { - public override AllowedCaller3 Read( + public override BetaToolBash20241022AllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -264,15 +201,15 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCaller3.Direct, - "code_execution_20250825" => AllowedCaller3.CodeExecution20250825, - _ => (AllowedCaller3)(-1), + "direct" => BetaToolBash20241022AllowedCaller.Direct, + "code_execution_20250825" => BetaToolBash20241022AllowedCaller.CodeExecution20250825, + _ => (BetaToolBash20241022AllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCaller3 value, + BetaToolBash20241022AllowedCaller value, JsonSerializerOptions options ) { @@ -280,8 +217,9 @@ JsonSerializerOptions options writer, value switch { - AllowedCaller3.Direct => "direct", - AllowedCaller3.CodeExecution20250825 => "code_execution_20250825", + BetaToolBash20241022AllowedCaller.Direct => "direct", + BetaToolBash20241022AllowedCaller.CodeExecution20250825 => + "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolBash20250124.cs b/src/Anthropic/Models/Beta/Messages/BetaToolBash20250124.cs index 020252c4..7ac213f0 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolBash20250124.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolBash20250124.cs @@ -19,57 +19,23 @@ public sealed record class BetaToolBash20250124 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList>? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + List> + >(this.RawData, "allowed_callers"); } init { @@ -78,10 +44,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -92,21 +55,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -115,13 +69,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -129,10 +77,7 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } @@ -140,12 +85,9 @@ public IReadOnlyList>? InputExamples { get { - if (!this._rawData.TryGetValue("input_examples", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawData, + "input_examples" ); } init @@ -155,22 +97,13 @@ public IReadOnlyList>? InputExamples return; } - this._rawData["input_examples"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "input_examples", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -178,13 +111,11 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } + /// public override void Validate() { if (!JsonElement.DeepEquals(this.Name, JsonSerializer.Deserialize("\"bash\""))) @@ -216,6 +147,9 @@ public BetaToolBash20250124() this.Type = JsonSerializer.Deserialize("\"bash_20250124\""); } + public BetaToolBash20250124(BetaToolBash20250124 betaToolBash20250124) + : base(betaToolBash20250124) { } + public BetaToolBash20250124(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -232,6 +166,7 @@ public BetaToolBash20250124(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaToolBash20250124 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -242,21 +177,23 @@ IReadOnlyDictionary rawData class BetaToolBash20250124FromRaw : IFromRaw { + /// public BetaToolBash20250124 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolBash20250124.FromRawUnchecked(rawData); } -[JsonConverter(typeof(AllowedCaller4Converter))] -public enum AllowedCaller4 +[JsonConverter(typeof(BetaToolBash20250124AllowedCallerConverter))] +public enum BetaToolBash20250124AllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCaller4Converter : JsonConverter +sealed class BetaToolBash20250124AllowedCallerConverter + : JsonConverter { - public override AllowedCaller4 Read( + public override BetaToolBash20250124AllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -264,15 +201,15 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCaller4.Direct, - "code_execution_20250825" => AllowedCaller4.CodeExecution20250825, - _ => (AllowedCaller4)(-1), + "direct" => BetaToolBash20250124AllowedCaller.Direct, + "code_execution_20250825" => BetaToolBash20250124AllowedCaller.CodeExecution20250825, + _ => (BetaToolBash20250124AllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCaller4 value, + BetaToolBash20250124AllowedCaller value, JsonSerializerOptions options ) { @@ -280,8 +217,9 @@ JsonSerializerOptions options writer, value switch { - AllowedCaller4.Direct => "direct", - AllowedCaller4.CodeExecution20250825 => "code_execution_20250825", + BetaToolBash20250124AllowedCaller.Direct => "direct", + BetaToolBash20250124AllowedCaller.CodeExecution20250825 => + "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolChoice.cs b/src/Anthropic/Models/Beta/Messages/BetaToolChoice.cs index 1c8332c7..a0a255d3 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolChoice.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolChoice.cs @@ -77,30 +77,112 @@ public BetaToolChoice(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickAuto(out var value)) { + /// // `value` is of type `BetaToolChoiceAuto` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickAuto([NotNullWhen(true)] out BetaToolChoiceAuto? value) { value = this.Value as BetaToolChoiceAuto; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickAny(out var value)) { + /// // `value` is of type `BetaToolChoiceAny` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickAny([NotNullWhen(true)] out BetaToolChoiceAny? value) { value = this.Value as BetaToolChoiceAny; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTool(out var value)) { + /// // `value` is of type `BetaToolChoiceTool` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTool([NotNullWhen(true)] out BetaToolChoiceTool? value) { value = this.Value as BetaToolChoiceTool; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickNone(out var value)) { + /// // `value` is of type `BetaToolChoiceNone` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickNone([NotNullWhen(true)] out BetaToolChoiceNone? value) { value = this.Value as BetaToolChoiceNone; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaToolChoiceAuto value) => {...}, + /// (BetaToolChoiceAny value) => {...}, + /// (BetaToolChoiceTool value) => {...}, + /// (BetaToolChoiceNone value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action auto, System::Action any, @@ -129,6 +211,29 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaToolChoiceAuto value) => {...}, + /// (BetaToolChoiceAny value) => {...}, + /// (BetaToolChoiceTool value) => {...}, + /// (BetaToolChoiceNone value) => {...} + /// ); + /// + /// + /// public T Match( System::Func auto, System::Func any, @@ -156,6 +261,16 @@ public T Match( public static implicit operator BetaToolChoice(BetaToolChoiceNone value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -164,6 +279,22 @@ public void Validate() "Data did not match any variant of BetaToolChoice" ); } + this.Switch( + (auto) => auto.Validate(), + (any) => any.Validate(), + (tool) => tool.Validate(), + (none) => none.Validate() + ); + } + + public virtual bool Equals(BetaToolChoice? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolChoiceAny.cs b/src/Anthropic/Models/Beta/Messages/BetaToolChoiceAny.cs index bb3035cd..24500b2d 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolChoiceAny.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolChoiceAny.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -17,23 +16,8 @@ public sealed record class BetaToolChoiceAny : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -44,13 +28,7 @@ public JsonElement Type /// public bool? DisableParallelToolUse { - get - { - if (!this._rawData.TryGetValue("disable_parallel_tool_use", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "disable_parallel_tool_use"); } init { if (value == null) @@ -58,13 +36,11 @@ public bool? DisableParallelToolUse return; } - this._rawData["disable_parallel_tool_use"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "disable_parallel_tool_use", value); } } + /// public override void Validate() { if (!JsonElement.DeepEquals(this.Type, JsonSerializer.Deserialize("\"any\""))) @@ -79,6 +55,9 @@ public BetaToolChoiceAny() this.Type = JsonSerializer.Deserialize("\"any\""); } + public BetaToolChoiceAny(BetaToolChoiceAny betaToolChoiceAny) + : base(betaToolChoiceAny) { } + public BetaToolChoiceAny(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -94,6 +73,7 @@ public BetaToolChoiceAny(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaToolChoiceAny FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -104,6 +84,7 @@ IReadOnlyDictionary rawData class BetaToolChoiceAnyFromRaw : IFromRaw { + /// public BetaToolChoiceAny FromRawUnchecked(IReadOnlyDictionary rawData) => BetaToolChoiceAny.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolChoiceAuto.cs b/src/Anthropic/Models/Beta/Messages/BetaToolChoiceAuto.cs index 763efaef..859a7f26 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolChoiceAuto.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolChoiceAuto.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -17,23 +16,8 @@ public sealed record class BetaToolChoiceAuto : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -44,13 +28,7 @@ public JsonElement Type /// public bool? DisableParallelToolUse { - get - { - if (!this._rawData.TryGetValue("disable_parallel_tool_use", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "disable_parallel_tool_use"); } init { if (value == null) @@ -58,13 +36,11 @@ public bool? DisableParallelToolUse return; } - this._rawData["disable_parallel_tool_use"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "disable_parallel_tool_use", value); } } + /// public override void Validate() { if (!JsonElement.DeepEquals(this.Type, JsonSerializer.Deserialize("\"auto\""))) @@ -79,6 +55,9 @@ public BetaToolChoiceAuto() this.Type = JsonSerializer.Deserialize("\"auto\""); } + public BetaToolChoiceAuto(BetaToolChoiceAuto betaToolChoiceAuto) + : base(betaToolChoiceAuto) { } + public BetaToolChoiceAuto(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -94,6 +73,7 @@ public BetaToolChoiceAuto(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaToolChoiceAuto FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -104,6 +84,7 @@ IReadOnlyDictionary rawData class BetaToolChoiceAutoFromRaw : IFromRaw { + /// public BetaToolChoiceAuto FromRawUnchecked(IReadOnlyDictionary rawData) => BetaToolChoiceAuto.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolChoiceNone.cs b/src/Anthropic/Models/Beta/Messages/BetaToolChoiceNone.cs index d9b1b9d3..14be82a7 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolChoiceNone.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolChoiceNone.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -17,25 +16,11 @@ public sealed record class BetaToolChoiceNone : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { if (!JsonElement.DeepEquals(this.Type, JsonSerializer.Deserialize("\"none\""))) @@ -49,6 +34,9 @@ public BetaToolChoiceNone() this.Type = JsonSerializer.Deserialize("\"none\""); } + public BetaToolChoiceNone(BetaToolChoiceNone betaToolChoiceNone) + : base(betaToolChoiceNone) { } + public BetaToolChoiceNone(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -64,6 +52,7 @@ public BetaToolChoiceNone(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaToolChoiceNone FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -74,6 +63,7 @@ IReadOnlyDictionary rawData class BetaToolChoiceNoneFromRaw : IFromRaw { + /// public BetaToolChoiceNone FromRawUnchecked(IReadOnlyDictionary rawData) => BetaToolChoiceNone.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolChoiceTool.cs b/src/Anthropic/Models/Beta/Messages/BetaToolChoiceTool.cs index 9b00ce2a..d7542b0b 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolChoiceTool.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolChoiceTool.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -20,48 +19,14 @@ public sealed record class BetaToolChoiceTool : ModelBase /// public required string Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentNullException("name") - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -72,13 +37,7 @@ public JsonElement Type /// public bool? DisableParallelToolUse { - get - { - if (!this._rawData.TryGetValue("disable_parallel_tool_use", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "disable_parallel_tool_use"); } init { if (value == null) @@ -86,13 +45,11 @@ public bool? DisableParallelToolUse return; } - this._rawData["disable_parallel_tool_use"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "disable_parallel_tool_use", value); } } + /// public override void Validate() { _ = this.Name; @@ -108,6 +65,9 @@ public BetaToolChoiceTool() this.Type = JsonSerializer.Deserialize("\"tool\""); } + public BetaToolChoiceTool(BetaToolChoiceTool betaToolChoiceTool) + : base(betaToolChoiceTool) { } + public BetaToolChoiceTool(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -123,6 +83,7 @@ public BetaToolChoiceTool(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaToolChoiceTool FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -140,6 +101,7 @@ public BetaToolChoiceTool(string name) class BetaToolChoiceToolFromRaw : IFromRaw { + /// public BetaToolChoiceTool FromRawUnchecked(IReadOnlyDictionary rawData) => BetaToolChoiceTool.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolComputerUse20241022.cs b/src/Anthropic/Models/Beta/Messages/BetaToolComputerUse20241022.cs index c9ecee9c..638172f0 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolComputerUse20241022.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolComputerUse20241022.cs @@ -19,26 +19,8 @@ public sealed record class BetaToolComputerUse20241022 : ModelBase /// public required long DisplayHeightPx { - get - { - if (!this._rawData.TryGetValue("display_height_px", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'display_height_px' cannot be null", - new System::ArgumentOutOfRangeException( - "display_height_px", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["display_height_px"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "display_height_px"); } + init { ModelBase.Set(this._rawData, "display_height_px", value); } } /// @@ -46,26 +28,8 @@ public required long DisplayHeightPx /// public required long DisplayWidthPx { - get - { - if (!this._rawData.TryGetValue("display_width_px", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'display_width_px' cannot be null", - new System::ArgumentOutOfRangeException( - "display_width_px", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["display_width_px"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "display_width_px"); } + init { ModelBase.Set(this._rawData, "display_width_px", value); } } /// @@ -75,57 +39,23 @@ public required long DisplayWidthPx /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList>? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + List> + >(this.RawData, "allowed_callers"); } init { @@ -134,10 +64,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -148,21 +75,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -171,13 +89,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -185,10 +97,7 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } @@ -197,32 +106,17 @@ public bool? DeferLoading /// public long? DisplayNumber { - get - { - if (!this._rawData.TryGetValue("display_number", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["display_number"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "display_number"); } + init { ModelBase.Set(this._rawData, "display_number", value); } } public IReadOnlyList>? InputExamples { get { - if (!this._rawData.TryGetValue("input_examples", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawData, + "input_examples" ); } init @@ -232,22 +126,13 @@ public IReadOnlyList>? InputExamples return; } - this._rawData["input_examples"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "input_examples", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -255,13 +140,11 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } + /// public override void Validate() { _ = this.DisplayHeightPx; @@ -301,6 +184,9 @@ public BetaToolComputerUse20241022() this.Type = JsonSerializer.Deserialize("\"computer_20241022\""); } + public BetaToolComputerUse20241022(BetaToolComputerUse20241022 betaToolComputerUse20241022) + : base(betaToolComputerUse20241022) { } + public BetaToolComputerUse20241022(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -317,6 +203,7 @@ public BetaToolComputerUse20241022(IReadOnlyDictionary rawD } #pragma warning restore CS8618 + /// public static BetaToolComputerUse20241022 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -327,21 +214,23 @@ IReadOnlyDictionary rawData class BetaToolComputerUse20241022FromRaw : IFromRaw { + /// public BetaToolComputerUse20241022 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolComputerUse20241022.FromRawUnchecked(rawData); } -[JsonConverter(typeof(AllowedCaller5Converter))] -public enum AllowedCaller5 +[JsonConverter(typeof(BetaToolComputerUse20241022AllowedCallerConverter))] +public enum BetaToolComputerUse20241022AllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCaller5Converter : JsonConverter +sealed class BetaToolComputerUse20241022AllowedCallerConverter + : JsonConverter { - public override AllowedCaller5 Read( + public override BetaToolComputerUse20241022AllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -349,15 +238,16 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCaller5.Direct, - "code_execution_20250825" => AllowedCaller5.CodeExecution20250825, - _ => (AllowedCaller5)(-1), + "direct" => BetaToolComputerUse20241022AllowedCaller.Direct, + "code_execution_20250825" => + BetaToolComputerUse20241022AllowedCaller.CodeExecution20250825, + _ => (BetaToolComputerUse20241022AllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCaller5 value, + BetaToolComputerUse20241022AllowedCaller value, JsonSerializerOptions options ) { @@ -365,8 +255,9 @@ JsonSerializerOptions options writer, value switch { - AllowedCaller5.Direct => "direct", - AllowedCaller5.CodeExecution20250825 => "code_execution_20250825", + BetaToolComputerUse20241022AllowedCaller.Direct => "direct", + BetaToolComputerUse20241022AllowedCaller.CodeExecution20250825 => + "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolComputerUse20250124.cs b/src/Anthropic/Models/Beta/Messages/BetaToolComputerUse20250124.cs index ac04ebb0..543fb19c 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolComputerUse20250124.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolComputerUse20250124.cs @@ -19,26 +19,8 @@ public sealed record class BetaToolComputerUse20250124 : ModelBase /// public required long DisplayHeightPx { - get - { - if (!this._rawData.TryGetValue("display_height_px", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'display_height_px' cannot be null", - new System::ArgumentOutOfRangeException( - "display_height_px", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["display_height_px"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "display_height_px"); } + init { ModelBase.Set(this._rawData, "display_height_px", value); } } /// @@ -46,26 +28,8 @@ public required long DisplayHeightPx /// public required long DisplayWidthPx { - get - { - if (!this._rawData.TryGetValue("display_width_px", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'display_width_px' cannot be null", - new System::ArgumentOutOfRangeException( - "display_width_px", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["display_width_px"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "display_width_px"); } + init { ModelBase.Set(this._rawData, "display_width_px", value); } } /// @@ -75,57 +39,23 @@ public required long DisplayWidthPx /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList>? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + List> + >(this.RawData, "allowed_callers"); } init { @@ -134,10 +64,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -148,21 +75,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -171,13 +89,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -185,10 +97,7 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } @@ -197,32 +106,17 @@ public bool? DeferLoading /// public long? DisplayNumber { - get - { - if (!this._rawData.TryGetValue("display_number", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["display_number"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "display_number"); } + init { ModelBase.Set(this._rawData, "display_number", value); } } public IReadOnlyList>? InputExamples { get { - if (!this._rawData.TryGetValue("input_examples", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawData, + "input_examples" ); } init @@ -232,22 +126,13 @@ public IReadOnlyList>? InputExamples return; } - this._rawData["input_examples"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "input_examples", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -255,13 +140,11 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } + /// public override void Validate() { _ = this.DisplayHeightPx; @@ -301,6 +184,9 @@ public BetaToolComputerUse20250124() this.Type = JsonSerializer.Deserialize("\"computer_20250124\""); } + public BetaToolComputerUse20250124(BetaToolComputerUse20250124 betaToolComputerUse20250124) + : base(betaToolComputerUse20250124) { } + public BetaToolComputerUse20250124(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -317,6 +203,7 @@ public BetaToolComputerUse20250124(IReadOnlyDictionary rawD } #pragma warning restore CS8618 + /// public static BetaToolComputerUse20250124 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -327,21 +214,23 @@ IReadOnlyDictionary rawData class BetaToolComputerUse20250124FromRaw : IFromRaw { + /// public BetaToolComputerUse20250124 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolComputerUse20250124.FromRawUnchecked(rawData); } -[JsonConverter(typeof(AllowedCaller6Converter))] -public enum AllowedCaller6 +[JsonConverter(typeof(BetaToolComputerUse20250124AllowedCallerConverter))] +public enum BetaToolComputerUse20250124AllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCaller6Converter : JsonConverter +sealed class BetaToolComputerUse20250124AllowedCallerConverter + : JsonConverter { - public override AllowedCaller6 Read( + public override BetaToolComputerUse20250124AllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -349,15 +238,16 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCaller6.Direct, - "code_execution_20250825" => AllowedCaller6.CodeExecution20250825, - _ => (AllowedCaller6)(-1), + "direct" => BetaToolComputerUse20250124AllowedCaller.Direct, + "code_execution_20250825" => + BetaToolComputerUse20250124AllowedCaller.CodeExecution20250825, + _ => (BetaToolComputerUse20250124AllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCaller6 value, + BetaToolComputerUse20250124AllowedCaller value, JsonSerializerOptions options ) { @@ -365,8 +255,9 @@ JsonSerializerOptions options writer, value switch { - AllowedCaller6.Direct => "direct", - AllowedCaller6.CodeExecution20250825 => "code_execution_20250825", + BetaToolComputerUse20250124AllowedCaller.Direct => "direct", + BetaToolComputerUse20250124AllowedCaller.CodeExecution20250825 => + "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolComputerUse20251124.cs b/src/Anthropic/Models/Beta/Messages/BetaToolComputerUse20251124.cs index b7d95872..f649ce5d 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolComputerUse20251124.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolComputerUse20251124.cs @@ -19,26 +19,8 @@ public sealed record class BetaToolComputerUse20251124 : ModelBase /// public required long DisplayHeightPx { - get - { - if (!this._rawData.TryGetValue("display_height_px", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'display_height_px' cannot be null", - new System::ArgumentOutOfRangeException( - "display_height_px", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["display_height_px"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "display_height_px"); } + init { ModelBase.Set(this._rawData, "display_height_px", value); } } /// @@ -46,26 +28,8 @@ public required long DisplayHeightPx /// public required long DisplayWidthPx { - get - { - if (!this._rawData.TryGetValue("display_width_px", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'display_width_px' cannot be null", - new System::ArgumentOutOfRangeException( - "display_width_px", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["display_width_px"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "display_width_px"); } + init { ModelBase.Set(this._rawData, "display_width_px", value); } } /// @@ -75,57 +39,23 @@ public required long DisplayWidthPx /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList>? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + List> + >(this.RawData, "allowed_callers"); } init { @@ -134,10 +64,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -148,21 +75,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -171,13 +89,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -185,10 +97,7 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } @@ -197,20 +106,8 @@ public bool? DeferLoading /// public long? DisplayNumber { - get - { - if (!this._rawData.TryGetValue("display_number", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["display_number"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "display_number"); } + init { ModelBase.Set(this._rawData, "display_number", value); } } /// @@ -218,13 +115,7 @@ public long? DisplayNumber /// public bool? EnableZoom { - get - { - if (!this._rawData.TryGetValue("enable_zoom", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "enable_zoom"); } init { if (value == null) @@ -232,10 +123,7 @@ public bool? EnableZoom return; } - this._rawData["enable_zoom"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "enable_zoom", value); } } @@ -243,12 +131,9 @@ public IReadOnlyList>? InputExamples { get { - if (!this._rawData.TryGetValue("input_examples", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawData, + "input_examples" ); } init @@ -258,22 +143,13 @@ public IReadOnlyList>? InputExamples return; } - this._rawData["input_examples"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "input_examples", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -281,13 +157,11 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } + /// public override void Validate() { _ = this.DisplayHeightPx; @@ -328,6 +202,9 @@ public BetaToolComputerUse20251124() this.Type = JsonSerializer.Deserialize("\"computer_20251124\""); } + public BetaToolComputerUse20251124(BetaToolComputerUse20251124 betaToolComputerUse20251124) + : base(betaToolComputerUse20251124) { } + public BetaToolComputerUse20251124(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -344,6 +221,7 @@ public BetaToolComputerUse20251124(IReadOnlyDictionary rawD } #pragma warning restore CS8618 + /// public static BetaToolComputerUse20251124 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -354,21 +232,23 @@ IReadOnlyDictionary rawData class BetaToolComputerUse20251124FromRaw : IFromRaw { + /// public BetaToolComputerUse20251124 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolComputerUse20251124.FromRawUnchecked(rawData); } -[JsonConverter(typeof(AllowedCaller7Converter))] -public enum AllowedCaller7 +[JsonConverter(typeof(BetaToolComputerUse20251124AllowedCallerConverter))] +public enum BetaToolComputerUse20251124AllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCaller7Converter : JsonConverter +sealed class BetaToolComputerUse20251124AllowedCallerConverter + : JsonConverter { - public override AllowedCaller7 Read( + public override BetaToolComputerUse20251124AllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -376,15 +256,16 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCaller7.Direct, - "code_execution_20250825" => AllowedCaller7.CodeExecution20250825, - _ => (AllowedCaller7)(-1), + "direct" => BetaToolComputerUse20251124AllowedCaller.Direct, + "code_execution_20250825" => + BetaToolComputerUse20251124AllowedCaller.CodeExecution20250825, + _ => (BetaToolComputerUse20251124AllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCaller7 value, + BetaToolComputerUse20251124AllowedCaller value, JsonSerializerOptions options ) { @@ -392,8 +273,9 @@ JsonSerializerOptions options writer, value switch { - AllowedCaller7.Direct => "direct", - AllowedCaller7.CodeExecution20250825 => "code_execution_20250825", + BetaToolComputerUse20251124AllowedCaller.Direct => "direct", + BetaToolComputerUse20251124AllowedCaller.CodeExecution20250825 => + "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolReferenceBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaToolReferenceBlock.cs index 1324b374..d2164cf4 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolReferenceBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolReferenceBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaToolReferenceBlock : ModelBase { public required string ToolName { - get - { - if (!this._rawData.TryGetValue("tool_name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_name' cannot be null", - new ArgumentOutOfRangeException("tool_name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_name' cannot be null", - new ArgumentNullException("tool_name") - ); - } - init - { - this._rawData["tool_name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_name"); } + init { ModelBase.Set(this._rawData, "tool_name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ToolName; @@ -77,6 +43,9 @@ public BetaToolReferenceBlock() this.Type = JsonSerializer.Deserialize("\"tool_reference\""); } + public BetaToolReferenceBlock(BetaToolReferenceBlock betaToolReferenceBlock) + : base(betaToolReferenceBlock) { } + public BetaToolReferenceBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BetaToolReferenceBlock(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaToolReferenceBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public BetaToolReferenceBlock(string toolName) class BetaToolReferenceBlockFromRaw : IFromRaw { + /// public BetaToolReferenceBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolReferenceBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolReferenceBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaToolReferenceBlockParam.cs index 661e96f3..afe4fe7f 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolReferenceBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolReferenceBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,48 +18,14 @@ public sealed record class BetaToolReferenceBlockParam : ModelBase { public required string ToolName { - get - { - if (!this._rawData.TryGetValue("tool_name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_name' cannot be null", - new ArgumentOutOfRangeException("tool_name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_name' cannot be null", - new ArgumentNullException("tool_name") - ); - } - init - { - this._rawData["tool_name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_name"); } + init { ModelBase.Set(this._rawData, "tool_name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -70,23 +35,15 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { _ = this.ToolName; @@ -107,6 +64,9 @@ public BetaToolReferenceBlockParam() this.Type = JsonSerializer.Deserialize("\"tool_reference\""); } + public BetaToolReferenceBlockParam(BetaToolReferenceBlockParam betaToolReferenceBlockParam) + : base(betaToolReferenceBlockParam) { } + public BetaToolReferenceBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -122,6 +82,7 @@ public BetaToolReferenceBlockParam(IReadOnlyDictionary rawD } #pragma warning restore CS8618 + /// public static BetaToolReferenceBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -139,6 +100,7 @@ public BetaToolReferenceBlockParam(string toolName) class BetaToolReferenceBlockParamFromRaw : IFromRaw { + /// public BetaToolReferenceBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolReferenceBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaToolResultBlockParam.cs index ae90ca27..a2cef870 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolResultBlockParam.cs @@ -15,51 +15,14 @@ public sealed record class BetaToolResultBlockParam : ModelBase { public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentOutOfRangeException( - "tool_use_id", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -69,33 +32,21 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } public BetaToolResultBlockParamContent? Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "content" ); } init @@ -105,22 +56,13 @@ public BetaToolResultBlockParamContent? Content return; } - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "content", value); } } public bool? IsError { - get - { - if (!this._rawData.TryGetValue("is_error", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "is_error"); } init { if (value == null) @@ -128,13 +70,11 @@ public bool? IsError return; } - this._rawData["is_error"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "is_error", value); } } + /// public override void Validate() { _ = this.ToolUseID; @@ -157,6 +97,9 @@ public BetaToolResultBlockParam() this.Type = JsonSerializer.Deserialize("\"tool_result\""); } + public BetaToolResultBlockParam(BetaToolResultBlockParam betaToolResultBlockParam) + : base(betaToolResultBlockParam) { } + public BetaToolResultBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -172,6 +115,7 @@ public BetaToolResultBlockParam(IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -189,6 +133,7 @@ public BetaToolResultBlockParam(string toolUseID) class BetaToolResultBlockParamFromRaw : IFromRaw { + /// public BetaToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolResultBlockParam.FromRawUnchecked(rawData); @@ -223,18 +168,68 @@ public BetaToolResultBlockParamContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBlocks(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBlocks([NotNullWhen(true)] out IReadOnlyList? value) { value = this.Value as IReadOnlyList; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch(System::Action @string, System::Action> blocks) { switch (this.Value) @@ -252,6 +247,27 @@ public void Switch(System::Action @string, System::Action + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match(System::Func @string, System::Func, T> blocks) { return this.Value switch @@ -269,6 +285,16 @@ public T Match(System::Func @string, System::Func value) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -278,6 +304,16 @@ public void Validate() ); } } + + public virtual bool Equals(BetaToolResultBlockParamContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } } sealed class BetaToolResultBlockParamContentConverter @@ -421,18 +457,63 @@ public Block(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaTextBlockParam(out var value)) { + /// // `value` is of type `BetaTextBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaTextBlockParam([NotNullWhen(true)] out BetaTextBlockParam? value) { value = this.Value as BetaTextBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaImageBlockParam(out var value)) { + /// // `value` is of type `BetaImageBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaImageBlockParam([NotNullWhen(true)] out BetaImageBlockParam? value) { value = this.Value as BetaImageBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaSearchResultBlockParam(out var value)) { + /// // `value` is of type `BetaSearchResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaSearchResultBlockParam( [NotNullWhen(true)] out BetaSearchResultBlockParam? value ) @@ -441,12 +522,42 @@ public bool TryPickBetaSearchResultBlockParam( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaRequestDocument(out var value)) { + /// // `value` is of type `BetaRequestDocumentBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaRequestDocument([NotNullWhen(true)] out BetaRequestDocumentBlock? value) { value = this.Value as BetaRequestDocumentBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolReferenceBlockParam(out var value)) { + /// // `value` is of type `BetaToolReferenceBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolReferenceBlockParam( [NotNullWhen(true)] out BetaToolReferenceBlockParam? value ) @@ -455,6 +566,29 @@ public bool TryPickBetaToolReferenceBlockParam( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaTextBlockParam value) => {...}, + /// (BetaImageBlockParam value) => {...}, + /// (BetaSearchResultBlockParam value) => {...}, + /// (BetaRequestDocumentBlock value) => {...}, + /// (BetaToolReferenceBlockParam value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaTextBlockParam, System::Action betaImageBlockParam, @@ -485,6 +619,30 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaTextBlockParam value) => {...}, + /// (BetaImageBlockParam value) => {...}, + /// (BetaSearchResultBlockParam value) => {...}, + /// (BetaRequestDocumentBlock value) => {...}, + /// (BetaToolReferenceBlockParam value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaTextBlockParam, System::Func betaImageBlockParam, @@ -514,12 +672,39 @@ public T Match( public static implicit operator Block(BetaToolReferenceBlockParam value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of Block"); } + this.Switch( + (betaTextBlockParam) => betaTextBlockParam.Validate(), + (betaImageBlockParam) => betaImageBlockParam.Validate(), + (betaSearchResultBlockParam) => betaSearchResultBlockParam.Validate(), + (betaRequestDocument) => betaRequestDocument.Validate(), + (betaToolReferenceBlockParam) => betaToolReferenceBlockParam.Validate() + ); + } + + public virtual bool Equals(Block? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolBm25_20251119.cs b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolBm25_20251119.cs index 789465ec..13d02a00 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolBm25_20251119.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolBm25_20251119.cs @@ -21,60 +21,31 @@ public sealed record class BetaToolSearchToolBm25_20251119 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public required ApiEnum Type { get { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "type" ); } + init { ModelBase.Set(this._rawData, "type", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList< + ApiEnum + >? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + List> + >(this.RawData, "allowed_callers"); } init { @@ -83,10 +54,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -97,21 +65,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -120,13 +79,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -134,22 +87,13 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -157,13 +101,11 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } + /// public override void Validate() { if ( @@ -190,6 +132,11 @@ public BetaToolSearchToolBm25_20251119() this.Name = JsonSerializer.Deserialize("\"tool_search_tool_bm25\""); } + public BetaToolSearchToolBm25_20251119( + BetaToolSearchToolBm25_20251119 betaToolSearchToolBm25_20251119 + ) + : base(betaToolSearchToolBm25_20251119) { } + public BetaToolSearchToolBm25_20251119(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -205,6 +152,7 @@ public BetaToolSearchToolBm25_20251119(IReadOnlyDictionary } #pragma warning restore CS8618 + /// public static BetaToolSearchToolBm25_20251119 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -224,6 +172,7 @@ ApiEnum type class BetaToolSearchToolBm25_20251119FromRaw : IFromRaw { + /// public BetaToolSearchToolBm25_20251119 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolSearchToolBm25_20251119.FromRawUnchecked(rawData); @@ -276,16 +225,17 @@ JsonSerializerOptions options } } -[JsonConverter(typeof(AllowedCaller8Converter))] -public enum AllowedCaller8 +[JsonConverter(typeof(BetaToolSearchToolBm25_20251119AllowedCallerConverter))] +public enum BetaToolSearchToolBm25_20251119AllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCaller8Converter : JsonConverter +sealed class BetaToolSearchToolBm25_20251119AllowedCallerConverter + : JsonConverter { - public override AllowedCaller8 Read( + public override BetaToolSearchToolBm25_20251119AllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -293,15 +243,16 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCaller8.Direct, - "code_execution_20250825" => AllowedCaller8.CodeExecution20250825, - _ => (AllowedCaller8)(-1), + "direct" => BetaToolSearchToolBm25_20251119AllowedCaller.Direct, + "code_execution_20250825" => + BetaToolSearchToolBm25_20251119AllowedCaller.CodeExecution20250825, + _ => (BetaToolSearchToolBm25_20251119AllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCaller8 value, + BetaToolSearchToolBm25_20251119AllowedCaller value, JsonSerializerOptions options ) { @@ -309,8 +260,9 @@ JsonSerializerOptions options writer, value switch { - AllowedCaller8.Direct => "direct", - AllowedCaller8.CodeExecution20250825 => "code_execution_20250825", + BetaToolSearchToolBm25_20251119AllowedCaller.Direct => "direct", + BetaToolSearchToolBm25_20251119AllowedCaller.CodeExecution20250825 => + "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolRegex20251119.cs b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolRegex20251119.cs index b62e2832..64944978 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolRegex20251119.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolRegex20251119.cs @@ -21,60 +21,31 @@ public sealed record class BetaToolSearchToolRegex20251119 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public required ApiEnum Type { get { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "type" ); } + init { ModelBase.Set(this._rawData, "type", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList< + ApiEnum + >? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + List> + >(this.RawData, "allowed_callers"); } init { @@ -83,10 +54,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -97,21 +65,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -120,13 +79,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -134,22 +87,13 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -157,13 +101,11 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } + /// public override void Validate() { if ( @@ -190,6 +132,11 @@ public BetaToolSearchToolRegex20251119() this.Name = JsonSerializer.Deserialize("\"tool_search_tool_regex\""); } + public BetaToolSearchToolRegex20251119( + BetaToolSearchToolRegex20251119 betaToolSearchToolRegex20251119 + ) + : base(betaToolSearchToolRegex20251119) { } + public BetaToolSearchToolRegex20251119(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -205,6 +152,7 @@ public BetaToolSearchToolRegex20251119(IReadOnlyDictionary } #pragma warning restore CS8618 + /// public static BetaToolSearchToolRegex20251119 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -224,6 +172,7 @@ ApiEnum type class BetaToolSearchToolRegex20251119FromRaw : IFromRaw { + /// public BetaToolSearchToolRegex20251119 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolSearchToolRegex20251119.FromRawUnchecked(rawData); @@ -276,16 +225,17 @@ JsonSerializerOptions options } } -[JsonConverter(typeof(AllowedCaller9Converter))] -public enum AllowedCaller9 +[JsonConverter(typeof(BetaToolSearchToolRegex20251119AllowedCallerConverter))] +public enum BetaToolSearchToolRegex20251119AllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCaller9Converter : JsonConverter +sealed class BetaToolSearchToolRegex20251119AllowedCallerConverter + : JsonConverter { - public override AllowedCaller9 Read( + public override BetaToolSearchToolRegex20251119AllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -293,15 +243,16 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCaller9.Direct, - "code_execution_20250825" => AllowedCaller9.CodeExecution20250825, - _ => (AllowedCaller9)(-1), + "direct" => BetaToolSearchToolRegex20251119AllowedCaller.Direct, + "code_execution_20250825" => + BetaToolSearchToolRegex20251119AllowedCaller.CodeExecution20250825, + _ => (BetaToolSearchToolRegex20251119AllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCaller9 value, + BetaToolSearchToolRegex20251119AllowedCaller value, JsonSerializerOptions options ) { @@ -309,8 +260,9 @@ JsonSerializerOptions options writer, value switch { - AllowedCaller9.Direct => "direct", - AllowedCaller9.CodeExecution20250825 => "code_execution_20250825", + BetaToolSearchToolRegex20251119AllowedCaller.Direct => "direct", + BetaToolSearchToolRegex20251119AllowedCaller.CodeExecution20250825 => + "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultBlock.cs index 5326341d..477303b9 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultBlock.cs @@ -18,79 +18,27 @@ public required BetaToolSearchToolResultBlockContent Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentOutOfRangeException( - "tool_use_id", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -111,6 +59,11 @@ public BetaToolSearchToolResultBlock() this.Type = JsonSerializer.Deserialize("\"tool_search_tool_result\""); } + public BetaToolSearchToolResultBlock( + BetaToolSearchToolResultBlock betaToolSearchToolResultBlock + ) + : base(betaToolSearchToolResultBlock) { } + public BetaToolSearchToolResultBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -126,6 +79,7 @@ public BetaToolSearchToolResultBlock(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaToolSearchToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -136,6 +90,7 @@ IReadOnlyDictionary rawData class BetaToolSearchToolResultBlockFromRaw : IFromRaw { + /// public BetaToolSearchToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolSearchToolResultBlock.FromRawUnchecked(rawData); @@ -187,6 +142,21 @@ public BetaToolSearchToolResultBlockContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolSearchToolResultError(out var value)) { + /// // `value` is of type `BetaToolSearchToolResultError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolSearchToolResultError( [NotNullWhen(true)] out BetaToolSearchToolResultError? value ) @@ -195,6 +165,21 @@ public bool TryPickBetaToolSearchToolResultError( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolSearchToolSearchResultBlock(out var value)) { + /// // `value` is of type `BetaToolSearchToolSearchResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolSearchToolSearchResultBlock( [NotNullWhen(true)] out BetaToolSearchToolSearchResultBlock? value ) @@ -203,6 +188,26 @@ public bool TryPickBetaToolSearchToolSearchResultBlock( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaToolSearchToolResultError value) => {...}, + /// (BetaToolSearchToolSearchResultBlock value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaToolSearchToolResultError, System::Action betaToolSearchToolSearchResultBlock @@ -223,6 +228,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaToolSearchToolResultError value) => {...}, + /// (BetaToolSearchToolSearchResultBlock value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaToolSearchToolResultError, System::Func betaToolSearchToolSearchResultBlock @@ -246,6 +272,16 @@ public static implicit operator BetaToolSearchToolResultBlockContent( BetaToolSearchToolSearchResultBlock value ) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -254,6 +290,20 @@ public void Validate() "Data did not match any variant of BetaToolSearchToolResultBlockContent" ); } + this.Switch( + (betaToolSearchToolResultError) => betaToolSearchToolResultError.Validate(), + (betaToolSearchToolSearchResultBlock) => betaToolSearchToolSearchResultBlock.Validate() + ); + } + + public virtual bool Equals(BetaToolSearchToolResultBlockContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultBlockParam.cs index ff9f9e49..a8949789 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultBlockParam.cs @@ -21,77 +21,24 @@ public required BetaToolSearchToolResultBlockParamContent Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentOutOfRangeException( - "tool_use_id", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -101,23 +48,15 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -139,6 +78,11 @@ public BetaToolSearchToolResultBlockParam() this.Type = JsonSerializer.Deserialize("\"tool_search_tool_result\""); } + public BetaToolSearchToolResultBlockParam( + BetaToolSearchToolResultBlockParam betaToolSearchToolResultBlockParam + ) + : base(betaToolSearchToolResultBlockParam) { } + public BetaToolSearchToolResultBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -154,6 +98,7 @@ public BetaToolSearchToolResultBlockParam(IReadOnlyDictionary public static BetaToolSearchToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -164,6 +109,7 @@ IReadOnlyDictionary rawData class BetaToolSearchToolResultBlockParamFromRaw : IFromRaw { + /// public BetaToolSearchToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolSearchToolResultBlockParam.FromRawUnchecked(rawData); @@ -215,6 +161,21 @@ public BetaToolSearchToolResultBlockParamContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolSearchToolResultErrorParam(out var value)) { + /// // `value` is of type `BetaToolSearchToolResultErrorParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolSearchToolResultErrorParam( [NotNullWhen(true)] out BetaToolSearchToolResultErrorParam? value ) @@ -223,6 +184,21 @@ public bool TryPickBetaToolSearchToolResultErrorParam( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolSearchToolSearchResultBlockParam(out var value)) { + /// // `value` is of type `BetaToolSearchToolSearchResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolSearchToolSearchResultBlockParam( [NotNullWhen(true)] out BetaToolSearchToolSearchResultBlockParam? value ) @@ -231,6 +207,26 @@ public bool TryPickBetaToolSearchToolSearchResultBlockParam( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaToolSearchToolResultErrorParam value) => {...}, + /// (BetaToolSearchToolSearchResultBlockParam value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaToolSearchToolResultErrorParam, System::Action betaToolSearchToolSearchResultBlockParam @@ -251,6 +247,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaToolSearchToolResultErrorParam value) => {...}, + /// (BetaToolSearchToolSearchResultBlockParam value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaToolSearchToolResultErrorParam, System::Func< @@ -278,6 +295,16 @@ public static implicit operator BetaToolSearchToolResultBlockParamContent( BetaToolSearchToolSearchResultBlockParam value ) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -286,6 +313,21 @@ public void Validate() "Data did not match any variant of BetaToolSearchToolResultBlockParamContent" ); } + this.Switch( + (betaToolSearchToolResultErrorParam) => betaToolSearchToolResultErrorParam.Validate(), + (betaToolSearchToolSearchResultBlockParam) => + betaToolSearchToolSearchResultBlockParam.Validate() + ); + } + + public virtual bool Equals(BetaToolSearchToolResultBlockParamContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultError.cs b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultError.cs index a5fcf216..07e8d65c 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultError.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultError.cs @@ -18,67 +18,26 @@ public required ApiEnum ErrorCod { get { - if (!this._rawData.TryGetValue("error_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error_code' cannot be null", - new System::ArgumentOutOfRangeException( - "error_code", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize< + return ModelBase.GetNotNullClass< ApiEnum - >(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["error_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + >(this.RawData, "error_code"); } + init { ModelBase.Set(this._rawData, "error_code", value); } } public required string? ErrorMessage { - get - { - if (!this._rawData.TryGetValue("error_message", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["error_message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "error_message"); } + init { ModelBase.Set(this._rawData, "error_message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.ErrorCode.Validate(); @@ -99,6 +58,11 @@ public BetaToolSearchToolResultError() this.Type = JsonSerializer.Deserialize("\"tool_search_tool_result_error\""); } + public BetaToolSearchToolResultError( + BetaToolSearchToolResultError betaToolSearchToolResultError + ) + : base(betaToolSearchToolResultError) { } + public BetaToolSearchToolResultError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -114,6 +78,7 @@ public BetaToolSearchToolResultError(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaToolSearchToolResultError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -124,6 +89,7 @@ IReadOnlyDictionary rawData class BetaToolSearchToolResultErrorFromRaw : IFromRaw { + /// public BetaToolSearchToolResultError FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolSearchToolResultError.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultErrorParam.cs b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultErrorParam.cs index 6480f26a..e3e290ed 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultErrorParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolResultErrorParam.cs @@ -21,49 +21,20 @@ public required ApiEnum Err { get { - if (!this._rawData.TryGetValue("error_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error_code' cannot be null", - new System::ArgumentOutOfRangeException( - "error_code", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize< + return ModelBase.GetNotNullClass< ApiEnum - >(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["error_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + >(this.RawData, "error_code"); } + init { ModelBase.Set(this._rawData, "error_code", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.ErrorCode.Validate(); @@ -83,6 +54,11 @@ public BetaToolSearchToolResultErrorParam() this.Type = JsonSerializer.Deserialize("\"tool_search_tool_result_error\""); } + public BetaToolSearchToolResultErrorParam( + BetaToolSearchToolResultErrorParam betaToolSearchToolResultErrorParam + ) + : base(betaToolSearchToolResultErrorParam) { } + public BetaToolSearchToolResultErrorParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -98,6 +74,7 @@ public BetaToolSearchToolResultErrorParam(IReadOnlyDictionary public static BetaToolSearchToolResultErrorParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -117,6 +94,7 @@ ApiEnum errorCode class BetaToolSearchToolResultErrorParamFromRaw : IFromRaw { + /// public BetaToolSearchToolResultErrorParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolSearchToolResultErrorParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolSearchResultBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolSearchResultBlock.cs index 83d04e50..a93af15a 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolSearchResultBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolSearchResultBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -21,51 +20,21 @@ public required IReadOnlyList ToolReferences { get { - if (!this._rawData.TryGetValue("tool_references", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_references' cannot be null", - new ArgumentOutOfRangeException("tool_references", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'tool_references' cannot be null", - new ArgumentNullException("tool_references") - ); - } - init - { - this._rawData["tool_references"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "tool_references" ); } + init { ModelBase.Set(this._rawData, "tool_references", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { foreach (var item in this.ToolReferences) @@ -88,6 +57,11 @@ public BetaToolSearchToolSearchResultBlock() this.Type = JsonSerializer.Deserialize("\"tool_search_tool_search_result\""); } + public BetaToolSearchToolSearchResultBlock( + BetaToolSearchToolSearchResultBlock betaToolSearchToolSearchResultBlock + ) + : base(betaToolSearchToolSearchResultBlock) { } + public BetaToolSearchToolSearchResultBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -103,6 +77,7 @@ public BetaToolSearchToolSearchResultBlock(IReadOnlyDictionary public static BetaToolSearchToolSearchResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -120,6 +95,7 @@ public BetaToolSearchToolSearchResultBlock(List toolRefe class BetaToolSearchToolSearchResultBlockFromRaw : IFromRaw { + /// public BetaToolSearchToolSearchResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolSearchToolSearchResultBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolSearchResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolSearchResultBlockParam.cs index 7efb064f..c5874f5c 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolSearchResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolSearchToolSearchResultBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -21,51 +20,21 @@ public required IReadOnlyList ToolReferences { get { - if (!this._rawData.TryGetValue("tool_references", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_references' cannot be null", - new ArgumentOutOfRangeException("tool_references", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'tool_references' cannot be null", - new ArgumentNullException("tool_references") - ); - } - init - { - this._rawData["tool_references"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "tool_references" ); } + init { ModelBase.Set(this._rawData, "tool_references", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { foreach (var item in this.ToolReferences) @@ -88,6 +57,11 @@ public BetaToolSearchToolSearchResultBlockParam() this.Type = JsonSerializer.Deserialize("\"tool_search_tool_search_result\""); } + public BetaToolSearchToolSearchResultBlockParam( + BetaToolSearchToolSearchResultBlockParam betaToolSearchToolSearchResultBlockParam + ) + : base(betaToolSearchToolSearchResultBlockParam) { } + public BetaToolSearchToolSearchResultBlockParam( IReadOnlyDictionary rawData ) @@ -105,6 +79,7 @@ IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaToolSearchToolSearchResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -125,6 +100,7 @@ List toolReferences class BetaToolSearchToolSearchResultBlockParamFromRaw : IFromRaw { + /// public BetaToolSearchToolSearchResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolSearchToolSearchResultBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20241022.cs b/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20241022.cs index b66a19ef..5dcc30eb 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20241022.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20241022.cs @@ -21,57 +21,23 @@ public sealed record class BetaToolTextEditor20241022 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList>? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + List> + >(this.RawData, "allowed_callers"); } init { @@ -80,10 +46,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -94,21 +57,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -117,13 +71,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -131,10 +79,7 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } @@ -142,12 +87,9 @@ public IReadOnlyList>? InputExamples { get { - if (!this._rawData.TryGetValue("input_examples", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawData, + "input_examples" ); } init @@ -157,22 +99,13 @@ public IReadOnlyList>? InputExamples return; } - this._rawData["input_examples"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "input_examples", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -180,13 +113,11 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } + /// public override void Validate() { if ( @@ -223,6 +154,9 @@ public BetaToolTextEditor20241022() this.Type = JsonSerializer.Deserialize("\"text_editor_20241022\""); } + public BetaToolTextEditor20241022(BetaToolTextEditor20241022 betaToolTextEditor20241022) + : base(betaToolTextEditor20241022) { } + public BetaToolTextEditor20241022(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -239,6 +173,7 @@ public BetaToolTextEditor20241022(IReadOnlyDictionary rawDa } #pragma warning restore CS8618 + /// public static BetaToolTextEditor20241022 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -249,21 +184,23 @@ IReadOnlyDictionary rawData class BetaToolTextEditor20241022FromRaw : IFromRaw { + /// public BetaToolTextEditor20241022 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolTextEditor20241022.FromRawUnchecked(rawData); } -[JsonConverter(typeof(AllowedCaller10Converter))] -public enum AllowedCaller10 +[JsonConverter(typeof(BetaToolTextEditor20241022AllowedCallerConverter))] +public enum BetaToolTextEditor20241022AllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCaller10Converter : JsonConverter +sealed class BetaToolTextEditor20241022AllowedCallerConverter + : JsonConverter { - public override AllowedCaller10 Read( + public override BetaToolTextEditor20241022AllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -271,15 +208,16 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCaller10.Direct, - "code_execution_20250825" => AllowedCaller10.CodeExecution20250825, - _ => (AllowedCaller10)(-1), + "direct" => BetaToolTextEditor20241022AllowedCaller.Direct, + "code_execution_20250825" => + BetaToolTextEditor20241022AllowedCaller.CodeExecution20250825, + _ => (BetaToolTextEditor20241022AllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCaller10 value, + BetaToolTextEditor20241022AllowedCaller value, JsonSerializerOptions options ) { @@ -287,8 +225,9 @@ JsonSerializerOptions options writer, value switch { - AllowedCaller10.Direct => "direct", - AllowedCaller10.CodeExecution20250825 => "code_execution_20250825", + BetaToolTextEditor20241022AllowedCaller.Direct => "direct", + BetaToolTextEditor20241022AllowedCaller.CodeExecution20250825 => + "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20250124.cs b/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20250124.cs index 4e3a58bd..6c540adb 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20250124.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20250124.cs @@ -21,57 +21,23 @@ public sealed record class BetaToolTextEditor20250124 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList>? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + List> + >(this.RawData, "allowed_callers"); } init { @@ -80,10 +46,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -94,21 +57,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -117,13 +71,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -131,10 +79,7 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } @@ -142,12 +87,9 @@ public IReadOnlyList>? InputExamples { get { - if (!this._rawData.TryGetValue("input_examples", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawData, + "input_examples" ); } init @@ -157,22 +99,13 @@ public IReadOnlyList>? InputExamples return; } - this._rawData["input_examples"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "input_examples", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -180,13 +113,11 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } + /// public override void Validate() { if ( @@ -223,6 +154,9 @@ public BetaToolTextEditor20250124() this.Type = JsonSerializer.Deserialize("\"text_editor_20250124\""); } + public BetaToolTextEditor20250124(BetaToolTextEditor20250124 betaToolTextEditor20250124) + : base(betaToolTextEditor20250124) { } + public BetaToolTextEditor20250124(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -239,6 +173,7 @@ public BetaToolTextEditor20250124(IReadOnlyDictionary rawDa } #pragma warning restore CS8618 + /// public static BetaToolTextEditor20250124 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -249,21 +184,23 @@ IReadOnlyDictionary rawData class BetaToolTextEditor20250124FromRaw : IFromRaw { + /// public BetaToolTextEditor20250124 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolTextEditor20250124.FromRawUnchecked(rawData); } -[JsonConverter(typeof(AllowedCaller11Converter))] -public enum AllowedCaller11 +[JsonConverter(typeof(BetaToolTextEditor20250124AllowedCallerConverter))] +public enum BetaToolTextEditor20250124AllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCaller11Converter : JsonConverter +sealed class BetaToolTextEditor20250124AllowedCallerConverter + : JsonConverter { - public override AllowedCaller11 Read( + public override BetaToolTextEditor20250124AllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -271,15 +208,16 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCaller11.Direct, - "code_execution_20250825" => AllowedCaller11.CodeExecution20250825, - _ => (AllowedCaller11)(-1), + "direct" => BetaToolTextEditor20250124AllowedCaller.Direct, + "code_execution_20250825" => + BetaToolTextEditor20250124AllowedCaller.CodeExecution20250825, + _ => (BetaToolTextEditor20250124AllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCaller11 value, + BetaToolTextEditor20250124AllowedCaller value, JsonSerializerOptions options ) { @@ -287,8 +225,9 @@ JsonSerializerOptions options writer, value switch { - AllowedCaller11.Direct => "direct", - AllowedCaller11.CodeExecution20250825 => "code_execution_20250825", + BetaToolTextEditor20250124AllowedCaller.Direct => "direct", + BetaToolTextEditor20250124AllowedCaller.CodeExecution20250825 => + "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20250429.cs b/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20250429.cs index d00de09e..39876ab0 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20250429.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20250429.cs @@ -21,57 +21,23 @@ public sealed record class BetaToolTextEditor20250429 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList>? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + List> + >(this.RawData, "allowed_callers"); } init { @@ -80,10 +46,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -94,21 +57,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -117,13 +71,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -131,10 +79,7 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } @@ -142,12 +87,9 @@ public IReadOnlyList>? InputExamples { get { - if (!this._rawData.TryGetValue("input_examples", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawData, + "input_examples" ); } init @@ -157,22 +99,13 @@ public IReadOnlyList>? InputExamples return; } - this._rawData["input_examples"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "input_examples", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -180,13 +113,11 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } + /// public override void Validate() { if ( @@ -223,6 +154,9 @@ public BetaToolTextEditor20250429() this.Type = JsonSerializer.Deserialize("\"text_editor_20250429\""); } + public BetaToolTextEditor20250429(BetaToolTextEditor20250429 betaToolTextEditor20250429) + : base(betaToolTextEditor20250429) { } + public BetaToolTextEditor20250429(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -239,6 +173,7 @@ public BetaToolTextEditor20250429(IReadOnlyDictionary rawDa } #pragma warning restore CS8618 + /// public static BetaToolTextEditor20250429 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -249,21 +184,23 @@ IReadOnlyDictionary rawData class BetaToolTextEditor20250429FromRaw : IFromRaw { + /// public BetaToolTextEditor20250429 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolTextEditor20250429.FromRawUnchecked(rawData); } -[JsonConverter(typeof(AllowedCaller12Converter))] -public enum AllowedCaller12 +[JsonConverter(typeof(BetaToolTextEditor20250429AllowedCallerConverter))] +public enum BetaToolTextEditor20250429AllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCaller12Converter : JsonConverter +sealed class BetaToolTextEditor20250429AllowedCallerConverter + : JsonConverter { - public override AllowedCaller12 Read( + public override BetaToolTextEditor20250429AllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -271,15 +208,16 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCaller12.Direct, - "code_execution_20250825" => AllowedCaller12.CodeExecution20250825, - _ => (AllowedCaller12)(-1), + "direct" => BetaToolTextEditor20250429AllowedCaller.Direct, + "code_execution_20250825" => + BetaToolTextEditor20250429AllowedCaller.CodeExecution20250825, + _ => (BetaToolTextEditor20250429AllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCaller12 value, + BetaToolTextEditor20250429AllowedCaller value, JsonSerializerOptions options ) { @@ -287,8 +225,9 @@ JsonSerializerOptions options writer, value switch { - AllowedCaller12.Direct => "direct", - AllowedCaller12.CodeExecution20250825 => "code_execution_20250825", + BetaToolTextEditor20250429AllowedCaller.Direct => "direct", + BetaToolTextEditor20250429AllowedCaller.CodeExecution20250825 => + "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20250728.cs b/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20250728.cs index 2edf0ea5..c341800c 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20250728.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolTextEditor20250728.cs @@ -21,57 +21,23 @@ public sealed record class BetaToolTextEditor20250728 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList>? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + List> + >(this.RawData, "allowed_callers"); } init { @@ -80,10 +46,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -94,21 +57,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -117,13 +71,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -131,10 +79,7 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } @@ -142,12 +87,9 @@ public IReadOnlyList>? InputExamples { get { - if (!this._rawData.TryGetValue("input_examples", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawData, + "input_examples" ); } init @@ -157,10 +99,7 @@ public IReadOnlyList>? InputExamples return; } - this._rawData["input_examples"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "input_examples", value); } } @@ -170,31 +109,13 @@ public IReadOnlyList>? InputExamples /// public long? MaxCharacters { - get - { - if (!this._rawData.TryGetValue("max_characters", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["max_characters"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "max_characters"); } + init { ModelBase.Set(this._rawData, "max_characters", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -202,13 +123,11 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } + /// public override void Validate() { if ( @@ -246,6 +165,9 @@ public BetaToolTextEditor20250728() this.Type = JsonSerializer.Deserialize("\"text_editor_20250728\""); } + public BetaToolTextEditor20250728(BetaToolTextEditor20250728 betaToolTextEditor20250728) + : base(betaToolTextEditor20250728) { } + public BetaToolTextEditor20250728(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -262,6 +184,7 @@ public BetaToolTextEditor20250728(IReadOnlyDictionary rawDa } #pragma warning restore CS8618 + /// public static BetaToolTextEditor20250728 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -272,21 +195,23 @@ IReadOnlyDictionary rawData class BetaToolTextEditor20250728FromRaw : IFromRaw { + /// public BetaToolTextEditor20250728 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolTextEditor20250728.FromRawUnchecked(rawData); } -[JsonConverter(typeof(AllowedCaller13Converter))] -public enum AllowedCaller13 +[JsonConverter(typeof(BetaToolTextEditor20250728AllowedCallerConverter))] +public enum BetaToolTextEditor20250728AllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCaller13Converter : JsonConverter +sealed class BetaToolTextEditor20250728AllowedCallerConverter + : JsonConverter { - public override AllowedCaller13 Read( + public override BetaToolTextEditor20250728AllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -294,15 +219,16 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCaller13.Direct, - "code_execution_20250825" => AllowedCaller13.CodeExecution20250825, - _ => (AllowedCaller13)(-1), + "direct" => BetaToolTextEditor20250728AllowedCaller.Direct, + "code_execution_20250825" => + BetaToolTextEditor20250728AllowedCaller.CodeExecution20250825, + _ => (BetaToolTextEditor20250728AllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCaller13 value, + BetaToolTextEditor20250728AllowedCaller value, JsonSerializerOptions options ) { @@ -310,8 +236,9 @@ JsonSerializerOptions options writer, value switch { - AllowedCaller13.Direct => "direct", - AllowedCaller13.CodeExecution20250825 => "code_execution_20250825", + BetaToolTextEditor20250728AllowedCaller.Direct => "direct", + BetaToolTextEditor20250728AllowedCaller.CodeExecution20250825 => + "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolUnion.cs b/src/Anthropic/Models/Beta/Messages/BetaToolUnion.cs index e863806f..4f6e2405 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolUnion.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolUnion.cs @@ -326,24 +326,84 @@ public BetaToolUnion(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaTool(out var value)) { + /// // `value` is of type `BetaTool` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaTool([NotNullWhen(true)] out BetaTool? value) { value = this.Value as BetaTool; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBash20241022(out var value)) { + /// // `value` is of type `BetaToolBash20241022` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBash20241022([NotNullWhen(true)] out BetaToolBash20241022? value) { value = this.Value as BetaToolBash20241022; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBash20250124(out var value)) { + /// // `value` is of type `BetaToolBash20250124` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBash20250124([NotNullWhen(true)] out BetaToolBash20250124? value) { value = this.Value as BetaToolBash20250124; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCodeExecutionTool20250522(out var value)) { + /// // `value` is of type `BetaCodeExecutionTool20250522` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCodeExecutionTool20250522( [NotNullWhen(true)] out BetaCodeExecutionTool20250522? value ) @@ -352,6 +412,21 @@ public bool TryPickCodeExecutionTool20250522( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCodeExecutionTool20250825(out var value)) { + /// // `value` is of type `BetaCodeExecutionTool20250825` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCodeExecutionTool20250825( [NotNullWhen(true)] out BetaCodeExecutionTool20250825? value ) @@ -360,6 +435,21 @@ public bool TryPickCodeExecutionTool20250825( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickComputerUse20241022(out var value)) { + /// // `value` is of type `BetaToolComputerUse20241022` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickComputerUse20241022( [NotNullWhen(true)] out BetaToolComputerUse20241022? value ) @@ -368,12 +458,42 @@ public bool TryPickComputerUse20241022( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickMemoryTool20250818(out var value)) { + /// // `value` is of type `BetaMemoryTool20250818` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickMemoryTool20250818([NotNullWhen(true)] out BetaMemoryTool20250818? value) { value = this.Value as BetaMemoryTool20250818; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickComputerUse20250124(out var value)) { + /// // `value` is of type `BetaToolComputerUse20250124` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickComputerUse20250124( [NotNullWhen(true)] out BetaToolComputerUse20250124? value ) @@ -382,12 +502,42 @@ public bool TryPickComputerUse20250124( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTextEditor20241022(out var value)) { + /// // `value` is of type `BetaToolTextEditor20241022` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTextEditor20241022([NotNullWhen(true)] out BetaToolTextEditor20241022? value) { value = this.Value as BetaToolTextEditor20241022; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickComputerUse20251124(out var value)) { + /// // `value` is of type `BetaToolComputerUse20251124` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickComputerUse20251124( [NotNullWhen(true)] out BetaToolComputerUse20251124? value ) @@ -396,24 +546,84 @@ public bool TryPickComputerUse20251124( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTextEditor20250124(out var value)) { + /// // `value` is of type `BetaToolTextEditor20250124` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTextEditor20250124([NotNullWhen(true)] out BetaToolTextEditor20250124? value) { value = this.Value as BetaToolTextEditor20250124; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTextEditor20250429(out var value)) { + /// // `value` is of type `BetaToolTextEditor20250429` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTextEditor20250429([NotNullWhen(true)] out BetaToolTextEditor20250429? value) { value = this.Value as BetaToolTextEditor20250429; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTextEditor20250728(out var value)) { + /// // `value` is of type `BetaToolTextEditor20250728` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTextEditor20250728([NotNullWhen(true)] out BetaToolTextEditor20250728? value) { value = this.Value as BetaToolTextEditor20250728; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickWebSearchTool20250305(out var value)) { + /// // `value` is of type `BetaWebSearchTool20250305` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickWebSearchTool20250305( [NotNullWhen(true)] out BetaWebSearchTool20250305? value ) @@ -422,12 +632,42 @@ public bool TryPickWebSearchTool20250305( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickWebFetchTool20250910(out var value)) { + /// // `value` is of type `BetaWebFetchTool20250910` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickWebFetchTool20250910([NotNullWhen(true)] out BetaWebFetchTool20250910? value) { value = this.Value as BetaWebFetchTool20250910; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickSearchToolBm25_20251119(out var value)) { + /// // `value` is of type `BetaToolSearchToolBm25_20251119` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickSearchToolBm25_20251119( [NotNullWhen(true)] out BetaToolSearchToolBm25_20251119? value ) @@ -436,6 +676,21 @@ public bool TryPickSearchToolBm25_20251119( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickSearchToolRegex20251119(out var value)) { + /// // `value` is of type `BetaToolSearchToolRegex20251119` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickSearchToolRegex20251119( [NotNullWhen(true)] out BetaToolSearchToolRegex20251119? value ) @@ -444,12 +699,63 @@ public bool TryPickSearchToolRegex20251119( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickMCPToolset(out var value)) { + /// // `value` is of type `BetaMCPToolset` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickMCPToolset([NotNullWhen(true)] out BetaMCPToolset? value) { value = this.Value as BetaMCPToolset; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaTool value) => {...}, + /// (BetaToolBash20241022 value) => {...}, + /// (BetaToolBash20250124 value) => {...}, + /// (BetaCodeExecutionTool20250522 value) => {...}, + /// (BetaCodeExecutionTool20250825 value) => {...}, + /// (BetaToolComputerUse20241022 value) => {...}, + /// (BetaMemoryTool20250818 value) => {...}, + /// (BetaToolComputerUse20250124 value) => {...}, + /// (BetaToolTextEditor20241022 value) => {...}, + /// (BetaToolComputerUse20251124 value) => {...}, + /// (BetaToolTextEditor20250124 value) => {...}, + /// (BetaToolTextEditor20250429 value) => {...}, + /// (BetaToolTextEditor20250728 value) => {...}, + /// (BetaWebSearchTool20250305 value) => {...}, + /// (BetaWebFetchTool20250910 value) => {...}, + /// (BetaToolSearchToolBm25_20251119 value) => {...}, + /// (BetaToolSearchToolRegex20251119 value) => {...}, + /// (BetaMCPToolset value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaTool, System::Action bash20241022, @@ -534,6 +840,43 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaTool value) => {...}, + /// (BetaToolBash20241022 value) => {...}, + /// (BetaToolBash20250124 value) => {...}, + /// (BetaCodeExecutionTool20250522 value) => {...}, + /// (BetaCodeExecutionTool20250825 value) => {...}, + /// (BetaToolComputerUse20241022 value) => {...}, + /// (BetaMemoryTool20250818 value) => {...}, + /// (BetaToolComputerUse20250124 value) => {...}, + /// (BetaToolTextEditor20241022 value) => {...}, + /// (BetaToolComputerUse20251124 value) => {...}, + /// (BetaToolTextEditor20250124 value) => {...}, + /// (BetaToolTextEditor20250429 value) => {...}, + /// (BetaToolTextEditor20250728 value) => {...}, + /// (BetaWebSearchTool20250305 value) => {...}, + /// (BetaWebFetchTool20250910 value) => {...}, + /// (BetaToolSearchToolBm25_20251119 value) => {...}, + /// (BetaToolSearchToolRegex20251119 value) => {...}, + /// (BetaMCPToolset value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaTool, System::Func bash20241022, @@ -621,6 +964,16 @@ public static implicit operator BetaToolUnion(BetaToolSearchToolRegex20251119 va public static implicit operator BetaToolUnion(BetaMCPToolset value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -629,6 +982,36 @@ public void Validate() "Data did not match any variant of BetaToolUnion" ); } + this.Switch( + (betaTool) => betaTool.Validate(), + (bash20241022) => bash20241022.Validate(), + (bash20250124) => bash20250124.Validate(), + (codeExecutionTool20250522) => codeExecutionTool20250522.Validate(), + (codeExecutionTool20250825) => codeExecutionTool20250825.Validate(), + (computerUse20241022) => computerUse20241022.Validate(), + (memoryTool20250818) => memoryTool20250818.Validate(), + (computerUse20250124) => computerUse20250124.Validate(), + (textEditor20241022) => textEditor20241022.Validate(), + (computerUse20251124) => computerUse20251124.Validate(), + (textEditor20250124) => textEditor20250124.Validate(), + (textEditor20250429) => textEditor20250429.Validate(), + (textEditor20250728) => textEditor20250728.Validate(), + (webSearchTool20250305) => webSearchTool20250305.Validate(), + (webFetchTool20250910) => webFetchTool20250910.Validate(), + (searchToolBm25_20251119) => searchToolBm25_20251119.Validate(), + (searchToolRegex20251119) => searchToolRegex20251119.Validate(), + (mcpToolset) => mcpToolset.Validate() + ); + } + + public virtual bool Equals(BetaToolUnion? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolUseBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaToolUseBlock.cs index cb86abaa..1e8eff17 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolUseBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolUseBlock.cs @@ -14,101 +14,32 @@ public sealed record class BetaToolUseBlock : ModelBase { public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new System::ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new System::ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } public required IReadOnlyDictionary Input { get { - if (!this._rawData.TryGetValue("input", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input' cannot be null", - new System::ArgumentOutOfRangeException("input", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'input' cannot be null", - new System::ArgumentNullException("input") - ); - } - init - { - this._rawData["input"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "input" ); } + init { ModelBase.Set(this._rawData, "input", value); } } public required string Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentNullException("name") - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -116,16 +47,7 @@ public JsonElement Type /// public BetaToolUseBlockCaller? Caller { - get - { - if (!this._rawData.TryGetValue("caller", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "caller"); } init { if (value == null) @@ -133,13 +55,11 @@ public BetaToolUseBlockCaller? Caller return; } - this._rawData["caller"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "caller", value); } } + /// public override void Validate() { _ = this.ID; @@ -162,6 +82,9 @@ public BetaToolUseBlock() this.Type = JsonSerializer.Deserialize("\"tool_use\""); } + public BetaToolUseBlock(BetaToolUseBlock betaToolUseBlock) + : base(betaToolUseBlock) { } + public BetaToolUseBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -177,6 +100,7 @@ public BetaToolUseBlock(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaToolUseBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -187,6 +111,7 @@ IReadOnlyDictionary rawData class BetaToolUseBlockFromRaw : IFromRaw { + /// public BetaToolUseBlock FromRawUnchecked(IReadOnlyDictionary rawData) => BetaToolUseBlock.FromRawUnchecked(rawData); } @@ -228,18 +153,68 @@ public BetaToolUseBlockCaller(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaDirect(out var value)) { + /// // `value` is of type `BetaDirectCaller` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaDirect([NotNullWhen(true)] out BetaDirectCaller? value) { value = this.Value as BetaDirectCaller; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaServerTool(out var value)) { + /// // `value` is of type `BetaServerToolCaller` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaServerTool([NotNullWhen(true)] out BetaServerToolCaller? value) { value = this.Value as BetaServerToolCaller; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaDirectCaller value) => {...}, + /// (BetaServerToolCaller value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaDirect, System::Action betaServerTool @@ -260,6 +235,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaDirectCaller value) => {...}, + /// (BetaServerToolCaller value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaDirect, System::Func betaServerTool @@ -280,6 +276,16 @@ public T Match( public static implicit operator BetaToolUseBlockCaller(BetaServerToolCaller value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -288,6 +294,20 @@ public void Validate() "Data did not match any variant of BetaToolUseBlockCaller" ); } + this.Switch( + (betaDirect) => betaDirect.Validate(), + (betaServerTool) => betaServerTool.Validate() + ); + } + + public virtual bool Equals(BetaToolUseBlockCaller? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolUseBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaToolUseBlockParam.cs index 72ac136d..283b8477 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolUseBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolUseBlockParam.cs @@ -14,101 +14,32 @@ public sealed record class BetaToolUseBlockParam : ModelBase { public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new System::ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new System::ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } public required IReadOnlyDictionary Input { get { - if (!this._rawData.TryGetValue("input", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input' cannot be null", - new System::ArgumentOutOfRangeException("input", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'input' cannot be null", - new System::ArgumentNullException("input") - ); - } - init - { - this._rawData["input"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "input" ); } + init { ModelBase.Set(this._rawData, "input", value); } } public required string Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentNullException("name") - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -118,21 +49,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -142,13 +64,7 @@ public BetaToolUseBlockParamCaller? Caller { get { - if (!this._rawData.TryGetValue("caller", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "caller"); } init { @@ -157,13 +73,11 @@ public BetaToolUseBlockParamCaller? Caller return; } - this._rawData["caller"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "caller", value); } } + /// public override void Validate() { _ = this.ID; @@ -187,6 +101,9 @@ public BetaToolUseBlockParam() this.Type = JsonSerializer.Deserialize("\"tool_use\""); } + public BetaToolUseBlockParam(BetaToolUseBlockParam betaToolUseBlockParam) + : base(betaToolUseBlockParam) { } + public BetaToolUseBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -202,6 +119,7 @@ public BetaToolUseBlockParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaToolUseBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -212,6 +130,7 @@ IReadOnlyDictionary rawData class BetaToolUseBlockParamFromRaw : IFromRaw { + /// public BetaToolUseBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaToolUseBlockParam.FromRawUnchecked(rawData); @@ -254,18 +173,68 @@ public BetaToolUseBlockParamCaller(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaDirect(out var value)) { + /// // `value` is of type `BetaDirectCaller` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaDirect([NotNullWhen(true)] out BetaDirectCaller? value) { value = this.Value as BetaDirectCaller; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaServerTool(out var value)) { + /// // `value` is of type `BetaServerToolCaller` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaServerTool([NotNullWhen(true)] out BetaServerToolCaller? value) { value = this.Value as BetaServerToolCaller; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaDirectCaller value) => {...}, + /// (BetaServerToolCaller value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaDirect, System::Action betaServerTool @@ -286,6 +255,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaDirectCaller value) => {...}, + /// (BetaServerToolCaller value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaDirect, System::Func betaServerTool @@ -307,6 +297,16 @@ public static implicit operator BetaToolUseBlockParamCaller(BetaDirectCaller val public static implicit operator BetaToolUseBlockParamCaller(BetaServerToolCaller value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -315,6 +315,20 @@ public void Validate() "Data did not match any variant of BetaToolUseBlockParamCaller" ); } + this.Switch( + (betaDirect) => betaDirect.Validate(), + (betaServerTool) => betaServerTool.Validate() + ); + } + + public virtual bool Equals(BetaToolUseBlockParamCaller? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolUsesKeep.cs b/src/Anthropic/Models/Beta/Messages/BetaToolUsesKeep.cs index f6c732e7..6f756ec1 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolUsesKeep.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolUsesKeep.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,46 +13,17 @@ public sealed record class BetaToolUsesKeep : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required long Value { - get - { - if (!this._rawData.TryGetValue("value", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'value' cannot be null", - new ArgumentOutOfRangeException("value", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["value"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "value"); } + init { ModelBase.Set(this._rawData, "value", value); } } + /// public override void Validate() { if ( @@ -73,6 +43,9 @@ public BetaToolUsesKeep() this.Type = JsonSerializer.Deserialize("\"tool_uses\""); } + public BetaToolUsesKeep(BetaToolUsesKeep betaToolUsesKeep) + : base(betaToolUsesKeep) { } + public BetaToolUsesKeep(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -88,6 +61,7 @@ public BetaToolUsesKeep(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaToolUsesKeep FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -105,6 +79,7 @@ public BetaToolUsesKeep(long value) class BetaToolUsesKeepFromRaw : IFromRaw { + /// public BetaToolUsesKeep FromRawUnchecked(IReadOnlyDictionary rawData) => BetaToolUsesKeep.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaToolUsesTrigger.cs b/src/Anthropic/Models/Beta/Messages/BetaToolUsesTrigger.cs index 4c44505e..c789fa8b 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaToolUsesTrigger.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaToolUsesTrigger.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,46 +13,17 @@ public sealed record class BetaToolUsesTrigger : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required long Value { - get - { - if (!this._rawData.TryGetValue("value", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'value' cannot be null", - new ArgumentOutOfRangeException("value", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["value"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "value"); } + init { ModelBase.Set(this._rawData, "value", value); } } + /// public override void Validate() { if ( @@ -73,6 +43,9 @@ public BetaToolUsesTrigger() this.Type = JsonSerializer.Deserialize("\"tool_uses\""); } + public BetaToolUsesTrigger(BetaToolUsesTrigger betaToolUsesTrigger) + : base(betaToolUsesTrigger) { } + public BetaToolUsesTrigger(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -88,6 +61,7 @@ public BetaToolUsesTrigger(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaToolUsesTrigger FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -105,6 +79,7 @@ public BetaToolUsesTrigger(long value) class BetaToolUsesTriggerFromRaw : IFromRaw { + /// public BetaToolUsesTrigger FromRawUnchecked(IReadOnlyDictionary rawData) => BetaToolUsesTrigger.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaURLImageSource.cs b/src/Anthropic/Models/Beta/Messages/BetaURLImageSource.cs index be0dc83e..95aff26b 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaURLImageSource.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaURLImageSource.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaURLImageSource : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required string URL { - get - { - if (!this._rawData.TryGetValue("url", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentOutOfRangeException("url", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentNullException("url") - ); - } - init - { - this._rawData["url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "url"); } + init { ModelBase.Set(this._rawData, "url", value); } } + /// public override void Validate() { if (!JsonElement.DeepEquals(this.Type, JsonSerializer.Deserialize("\"url\""))) @@ -72,6 +38,9 @@ public BetaURLImageSource() this.Type = JsonSerializer.Deserialize("\"url\""); } + public BetaURLImageSource(BetaURLImageSource betaURLImageSource) + : base(betaURLImageSource) { } + public BetaURLImageSource(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -87,6 +56,7 @@ public BetaURLImageSource(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaURLImageSource FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -104,6 +74,7 @@ public BetaURLImageSource(string url) class BetaURLImageSourceFromRaw : IFromRaw { + /// public BetaURLImageSource FromRawUnchecked(IReadOnlyDictionary rawData) => BetaURLImageSource.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaURLPDFSource.cs b/src/Anthropic/Models/Beta/Messages/BetaURLPDFSource.cs index 1758ae34..b84eb5c5 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaURLPDFSource.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaURLPDFSource.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BetaURLPDFSource : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required string URL { - get - { - if (!this._rawData.TryGetValue("url", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentOutOfRangeException("url", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentNullException("url") - ); - } - init - { - this._rawData["url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "url"); } + init { ModelBase.Set(this._rawData, "url", value); } } + /// public override void Validate() { if (!JsonElement.DeepEquals(this.Type, JsonSerializer.Deserialize("\"url\""))) @@ -72,6 +38,9 @@ public BetaURLPDFSource() this.Type = JsonSerializer.Deserialize("\"url\""); } + public BetaURLPDFSource(BetaURLPDFSource betaUrlpdfSource) + : base(betaUrlpdfSource) { } + public BetaURLPDFSource(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -87,6 +56,7 @@ public BetaURLPDFSource(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaURLPDFSource FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -104,6 +74,7 @@ public BetaURLPDFSource(string url) class BetaURLPDFSourceFromRaw : IFromRaw { + /// public BetaURLPDFSource FromRawUnchecked(IReadOnlyDictionary rawData) => BetaURLPDFSource.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaUsage.cs b/src/Anthropic/Models/Beta/Messages/BetaUsage.cs index 69edcd23..7d8434cb 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaUsage.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaUsage.cs @@ -19,21 +19,9 @@ public required BetaCacheCreation? CacheCreation { get { - if (!this._rawData.TryGetValue("cache_creation", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_creation"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "cache_creation"); } + init { ModelBase.Set(this._rawData, "cache_creation", value); } } /// @@ -43,18 +31,9 @@ public required long? CacheCreationInputTokens { get { - if (!this._rawData.TryGetValue("cache_creation_input_tokens", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["cache_creation_input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableStruct(this.RawData, "cache_creation_input_tokens"); } + init { ModelBase.Set(this._rawData, "cache_creation_input_tokens", value); } } /// @@ -62,20 +41,8 @@ public required long? CacheCreationInputTokens /// public required long? CacheReadInputTokens { - get - { - if (!this._rawData.TryGetValue("cache_read_input_tokens", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["cache_read_input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "cache_read_input_tokens"); } + init { ModelBase.Set(this._rawData, "cache_read_input_tokens", value); } } /// @@ -83,26 +50,8 @@ public required long? CacheReadInputTokens /// public required long InputTokens { - get - { - if (!this._rawData.TryGetValue("input_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input_tokens' cannot be null", - new System::ArgumentOutOfRangeException( - "input_tokens", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "input_tokens"); } + init { ModelBase.Set(this._rawData, "input_tokens", value); } } /// @@ -110,26 +59,8 @@ public required long InputTokens /// public required long OutputTokens { - get - { - if (!this._rawData.TryGetValue("output_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'output_tokens' cannot be null", - new System::ArgumentOutOfRangeException( - "output_tokens", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["output_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "output_tokens"); } + init { ModelBase.Set(this._rawData, "output_tokens", value); } } /// @@ -139,21 +70,9 @@ public required BetaServerToolUsage? ServerToolUse { get { - if (!this._rawData.TryGetValue("server_tool_use", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["server_tool_use"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "server_tool_use"); } + init { ModelBase.Set(this._rawData, "server_tool_use", value); } } /// @@ -163,23 +82,15 @@ public required ApiEnum? ServiceTier { get { - if (!this._rawData.TryGetValue("service_tier", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["service_tier"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawData, + "service_tier" ); } + init { ModelBase.Set(this._rawData, "service_tier", value); } } + /// public override void Validate() { this.CacheCreation?.Validate(); @@ -193,6 +104,9 @@ public override void Validate() public BetaUsage() { } + public BetaUsage(BetaUsage betaUsage) + : base(betaUsage) { } + public BetaUsage(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -206,6 +120,7 @@ public BetaUsage(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaUsage FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -214,6 +129,7 @@ public static BetaUsage FromRawUnchecked(IReadOnlyDictionary { + /// public BetaUsage FromRawUnchecked(IReadOnlyDictionary rawData) => BetaUsage.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebFetchBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaWebFetchBlock.cs index 9f60990e..889c5ac9 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebFetchBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebFetchBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,30 +13,8 @@ public sealed record class BetaWebFetchBlock : ModelBase { public required BetaDocumentBlock Content { - get - { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "content"); } + init { ModelBase.Set(this._rawData, "content", value); } } /// @@ -45,41 +22,14 @@ public required BetaDocumentBlock Content /// public required string? RetrievedAt { - get - { - if (!this._rawData.TryGetValue("retrieved_at", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["retrieved_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "retrieved_at"); } + init { ModelBase.Set(this._rawData, "retrieved_at", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -87,29 +37,11 @@ public JsonElement Type /// public required string URL { - get - { - if (!this._rawData.TryGetValue("url", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentOutOfRangeException("url", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentNullException("url") - ); - } - init - { - this._rawData["url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "url"); } + init { ModelBase.Set(this._rawData, "url", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -131,6 +63,9 @@ public BetaWebFetchBlock() this.Type = JsonSerializer.Deserialize("\"web_fetch_result\""); } + public BetaWebFetchBlock(BetaWebFetchBlock betaWebFetchBlock) + : base(betaWebFetchBlock) { } + public BetaWebFetchBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -146,6 +81,7 @@ public BetaWebFetchBlock(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaWebFetchBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -156,6 +92,7 @@ IReadOnlyDictionary rawData class BetaWebFetchBlockFromRaw : IFromRaw { + /// public BetaWebFetchBlock FromRawUnchecked(IReadOnlyDictionary rawData) => BetaWebFetchBlock.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebFetchBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaWebFetchBlockParam.cs index bff6d926..9f500dc8 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebFetchBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebFetchBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,51 +13,14 @@ public sealed record class BetaWebFetchBlockParam : ModelBase { public required BetaRequestDocumentBlock Content { - get - { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "content"); } + init { ModelBase.Set(this._rawData, "content", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -66,27 +28,8 @@ public JsonElement Type /// public required string URL { - get - { - if (!this._rawData.TryGetValue("url", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentOutOfRangeException("url", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentNullException("url") - ); - } - init - { - this._rawData["url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "url"); } + init { ModelBase.Set(this._rawData, "url", value); } } /// @@ -94,22 +37,11 @@ public required string URL /// public string? RetrievedAt { - get - { - if (!this._rawData.TryGetValue("retrieved_at", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["retrieved_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "retrieved_at"); } + init { ModelBase.Set(this._rawData, "retrieved_at", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -131,6 +63,9 @@ public BetaWebFetchBlockParam() this.Type = JsonSerializer.Deserialize("\"web_fetch_result\""); } + public BetaWebFetchBlockParam(BetaWebFetchBlockParam betaWebFetchBlockParam) + : base(betaWebFetchBlockParam) { } + public BetaWebFetchBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -146,6 +81,7 @@ public BetaWebFetchBlockParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaWebFetchBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -156,6 +92,7 @@ IReadOnlyDictionary rawData class BetaWebFetchBlockParamFromRaw : IFromRaw { + /// public BetaWebFetchBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaWebFetchBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebFetchTool20250910.cs b/src/Anthropic/Models/Beta/Messages/BetaWebFetchTool20250910.cs index 8d72d7a2..7bc31f80 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebFetchTool20250910.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebFetchTool20250910.cs @@ -19,57 +19,23 @@ public sealed record class BetaWebFetchTool20250910 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList>? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + List> + >(this.RawData, "allowed_callers"); } init { @@ -78,10 +44,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -90,20 +53,8 @@ public IReadOnlyList>? AllowedCallers /// public IReadOnlyList? AllowedDomains { - get - { - if (!this._rawData.TryGetValue("allowed_domains", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["allowed_domains"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "allowed_domains"); } + init { ModelBase.Set(this._rawData, "allowed_domains", value); } } /// @@ -111,20 +62,8 @@ public IReadOnlyList? AllowedDomains /// public IReadOnlyList? BlockedDomains { - get - { - if (!this._rawData.TryGetValue("blocked_domains", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["blocked_domains"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "blocked_domains"); } + init { ModelBase.Set(this._rawData, "blocked_domains", value); } } /// @@ -134,21 +73,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -158,21 +88,9 @@ public BetaCitationsConfigParam? Citations { get { - if (!this._rawData.TryGetValue("citations", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["citations"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "citations"); } + init { ModelBase.Set(this._rawData, "citations", value); } } /// @@ -181,13 +99,7 @@ public BetaCitationsConfigParam? Citations /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -195,10 +107,7 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } @@ -208,20 +117,8 @@ public bool? DeferLoading /// public long? MaxContentTokens { - get - { - if (!this._rawData.TryGetValue("max_content_tokens", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["max_content_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "max_content_tokens"); } + init { ModelBase.Set(this._rawData, "max_content_tokens", value); } } /// @@ -229,31 +126,13 @@ public long? MaxContentTokens /// public long? MaxUses { - get - { - if (!this._rawData.TryGetValue("max_uses", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["max_uses"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "max_uses"); } + init { ModelBase.Set(this._rawData, "max_uses", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -261,13 +140,11 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } + /// public override void Validate() { if ( @@ -308,6 +185,9 @@ public BetaWebFetchTool20250910() this.Type = JsonSerializer.Deserialize("\"web_fetch_20250910\""); } + public BetaWebFetchTool20250910(BetaWebFetchTool20250910 betaWebFetchTool20250910) + : base(betaWebFetchTool20250910) { } + public BetaWebFetchTool20250910(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -324,6 +204,7 @@ public BetaWebFetchTool20250910(IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaWebFetchTool20250910 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -334,21 +215,23 @@ IReadOnlyDictionary rawData class BetaWebFetchTool20250910FromRaw : IFromRaw { + /// public BetaWebFetchTool20250910 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaWebFetchTool20250910.FromRawUnchecked(rawData); } -[JsonConverter(typeof(AllowedCaller14Converter))] -public enum AllowedCaller14 +[JsonConverter(typeof(BetaWebFetchTool20250910AllowedCallerConverter))] +public enum BetaWebFetchTool20250910AllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCaller14Converter : JsonConverter +sealed class BetaWebFetchTool20250910AllowedCallerConverter + : JsonConverter { - public override AllowedCaller14 Read( + public override BetaWebFetchTool20250910AllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -356,15 +239,16 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCaller14.Direct, - "code_execution_20250825" => AllowedCaller14.CodeExecution20250825, - _ => (AllowedCaller14)(-1), + "direct" => BetaWebFetchTool20250910AllowedCaller.Direct, + "code_execution_20250825" => + BetaWebFetchTool20250910AllowedCaller.CodeExecution20250825, + _ => (BetaWebFetchTool20250910AllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCaller14 value, + BetaWebFetchTool20250910AllowedCaller value, JsonSerializerOptions options ) { @@ -372,8 +256,9 @@ JsonSerializerOptions options writer, value switch { - AllowedCaller14.Direct => "direct", - AllowedCaller14.CodeExecution20250825 => "code_execution_20250825", + BetaWebFetchTool20250910AllowedCaller.Direct => "direct", + BetaWebFetchTool20250910AllowedCaller.CodeExecution20250825 => + "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultBlock.cs index bf4bea0d..cc5679bf 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultBlock.cs @@ -18,79 +18,27 @@ public required BetaWebFetchToolResultBlockContent Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentOutOfRangeException( - "tool_use_id", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -111,6 +59,9 @@ public BetaWebFetchToolResultBlock() this.Type = JsonSerializer.Deserialize("\"web_fetch_tool_result\""); } + public BetaWebFetchToolResultBlock(BetaWebFetchToolResultBlock betaWebFetchToolResultBlock) + : base(betaWebFetchToolResultBlock) { } + public BetaWebFetchToolResultBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -126,6 +77,7 @@ public BetaWebFetchToolResultBlock(IReadOnlyDictionary rawD } #pragma warning restore CS8618 + /// public static BetaWebFetchToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -136,6 +88,7 @@ IReadOnlyDictionary rawData class BetaWebFetchToolResultBlockFromRaw : IFromRaw { + /// public BetaWebFetchToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaWebFetchToolResultBlock.FromRawUnchecked(rawData); @@ -184,6 +137,21 @@ public BetaWebFetchToolResultBlockContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaWebFetchToolResultErrorBlock(out var value)) { + /// // `value` is of type `BetaWebFetchToolResultErrorBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaWebFetchToolResultErrorBlock( [NotNullWhen(true)] out BetaWebFetchToolResultErrorBlock? value ) @@ -192,12 +160,47 @@ public bool TryPickBetaWebFetchToolResultErrorBlock( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaWebFetchBlock(out var value)) { + /// // `value` is of type `BetaWebFetchBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaWebFetchBlock([NotNullWhen(true)] out BetaWebFetchBlock? value) { value = this.Value as BetaWebFetchBlock; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaWebFetchToolResultErrorBlock value) => {...}, + /// (BetaWebFetchBlock value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaWebFetchToolResultErrorBlock, System::Action betaWebFetchBlock @@ -218,6 +221,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaWebFetchToolResultErrorBlock value) => {...}, + /// (BetaWebFetchBlock value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaWebFetchToolResultErrorBlock, System::Func betaWebFetchBlock @@ -240,6 +264,16 @@ BetaWebFetchToolResultErrorBlock value public static implicit operator BetaWebFetchToolResultBlockContent(BetaWebFetchBlock value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -248,6 +282,20 @@ public void Validate() "Data did not match any variant of BetaWebFetchToolResultBlockContent" ); } + this.Switch( + (betaWebFetchToolResultErrorBlock) => betaWebFetchToolResultErrorBlock.Validate(), + (betaWebFetchBlock) => betaWebFetchBlock.Validate() + ); + } + + public virtual bool Equals(BetaWebFetchToolResultBlockContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultBlockParam.cs index 8c3c6883..9c7f727c 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultBlockParam.cs @@ -21,77 +21,24 @@ public required BetaWebFetchToolResultBlockParamContent Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentOutOfRangeException( - "tool_use_id", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -101,23 +48,15 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -139,6 +78,11 @@ public BetaWebFetchToolResultBlockParam() this.Type = JsonSerializer.Deserialize("\"web_fetch_tool_result\""); } + public BetaWebFetchToolResultBlockParam( + BetaWebFetchToolResultBlockParam betaWebFetchToolResultBlockParam + ) + : base(betaWebFetchToolResultBlockParam) { } + public BetaWebFetchToolResultBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -154,6 +98,7 @@ public BetaWebFetchToolResultBlockParam(IReadOnlyDictionary } #pragma warning restore CS8618 + /// public static BetaWebFetchToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -164,6 +109,7 @@ IReadOnlyDictionary rawData class BetaWebFetchToolResultBlockParamFromRaw : IFromRaw { + /// public BetaWebFetchToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaWebFetchToolResultBlockParam.FromRawUnchecked(rawData); @@ -215,6 +161,21 @@ public BetaWebFetchToolResultBlockParamContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaWebFetchToolResultErrorBlockParam(out var value)) { + /// // `value` is of type `BetaWebFetchToolResultErrorBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaWebFetchToolResultErrorBlockParam( [NotNullWhen(true)] out BetaWebFetchToolResultErrorBlockParam? value ) @@ -223,12 +184,47 @@ public bool TryPickBetaWebFetchToolResultErrorBlockParam( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaWebFetchBlockParam(out var value)) { + /// // `value` is of type `BetaWebFetchBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaWebFetchBlockParam([NotNullWhen(true)] out BetaWebFetchBlockParam? value) { value = this.Value as BetaWebFetchBlockParam; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaWebFetchToolResultErrorBlockParam value) => {...}, + /// (BetaWebFetchBlockParam value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaWebFetchToolResultErrorBlockParam, System::Action betaWebFetchBlockParam @@ -249,6 +245,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaWebFetchToolResultErrorBlockParam value) => {...}, + /// (BetaWebFetchBlockParam value) => {...} + /// ); + /// + /// + /// public T Match( System::Func< BetaWebFetchToolResultErrorBlockParam, @@ -277,6 +294,16 @@ public static implicit operator BetaWebFetchToolResultBlockParamContent( BetaWebFetchBlockParam value ) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -285,6 +312,21 @@ public void Validate() "Data did not match any variant of BetaWebFetchToolResultBlockParamContent" ); } + this.Switch( + (betaWebFetchToolResultErrorBlockParam) => + betaWebFetchToolResultErrorBlockParam.Validate(), + (betaWebFetchBlockParam) => betaWebFetchBlockParam.Validate() + ); + } + + public virtual bool Equals(BetaWebFetchToolResultBlockParamContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultErrorBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultErrorBlock.cs index 4a10c597..fd279b46 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultErrorBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultErrorBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -21,47 +20,21 @@ public required ApiEnum ErrorCode { get { - if (!this._rawData.TryGetValue("error_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error_code' cannot be null", - new ArgumentOutOfRangeException("error_code", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["error_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "error_code" ); } + init { ModelBase.Set(this._rawData, "error_code", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.ErrorCode.Validate(); @@ -81,6 +54,11 @@ public BetaWebFetchToolResultErrorBlock() this.Type = JsonSerializer.Deserialize("\"web_fetch_tool_result_error\""); } + public BetaWebFetchToolResultErrorBlock( + BetaWebFetchToolResultErrorBlock betaWebFetchToolResultErrorBlock + ) + : base(betaWebFetchToolResultErrorBlock) { } + public BetaWebFetchToolResultErrorBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -96,6 +74,7 @@ public BetaWebFetchToolResultErrorBlock(IReadOnlyDictionary } #pragma warning restore CS8618 + /// public static BetaWebFetchToolResultErrorBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -115,6 +94,7 @@ ApiEnum errorCode class BetaWebFetchToolResultErrorBlockFromRaw : IFromRaw { + /// public BetaWebFetchToolResultErrorBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaWebFetchToolResultErrorBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultErrorBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultErrorBlockParam.cs index a1d67f6f..685f1ddf 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultErrorBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebFetchToolResultErrorBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -21,47 +20,21 @@ public required ApiEnum ErrorCode { get { - if (!this._rawData.TryGetValue("error_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error_code' cannot be null", - new ArgumentOutOfRangeException("error_code", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["error_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "error_code" ); } + init { ModelBase.Set(this._rawData, "error_code", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.ErrorCode.Validate(); @@ -81,6 +54,11 @@ public BetaWebFetchToolResultErrorBlockParam() this.Type = JsonSerializer.Deserialize("\"web_fetch_tool_result_error\""); } + public BetaWebFetchToolResultErrorBlockParam( + BetaWebFetchToolResultErrorBlockParam betaWebFetchToolResultErrorBlockParam + ) + : base(betaWebFetchToolResultErrorBlockParam) { } + public BetaWebFetchToolResultErrorBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -96,6 +74,7 @@ public BetaWebFetchToolResultErrorBlockParam(IReadOnlyDictionary public static BetaWebFetchToolResultErrorBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -115,6 +94,7 @@ ApiEnum errorCode class BetaWebFetchToolResultErrorBlockParamFromRaw : IFromRaw { + /// public BetaWebFetchToolResultErrorBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaWebFetchToolResultErrorBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebSearchResultBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaWebSearchResultBlock.cs index 0967f940..21795352 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebSearchResultBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebSearchResultBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,121 +13,35 @@ public sealed record class BetaWebSearchResultBlock : ModelBase { public required string EncryptedContent { - get - { - if (!this._rawData.TryGetValue("encrypted_content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'encrypted_content' cannot be null", - new ArgumentOutOfRangeException( - "encrypted_content", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'encrypted_content' cannot be null", - new ArgumentNullException("encrypted_content") - ); - } - init - { - this._rawData["encrypted_content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "encrypted_content"); } + init { ModelBase.Set(this._rawData, "encrypted_content", value); } } public required string? PageAge { - get - { - if (!this._rawData.TryGetValue("page_age", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["page_age"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "page_age"); } + init { ModelBase.Set(this._rawData, "page_age", value); } } public required string Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'title' cannot be null", - new ArgumentOutOfRangeException("title", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'title' cannot be null", - new ArgumentNullException("title") - ); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required string URL { - get - { - if (!this._rawData.TryGetValue("url", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentOutOfRangeException("url", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentNullException("url") - ); - } - init - { - this._rawData["url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "url"); } + init { ModelBase.Set(this._rawData, "url", value); } } + /// public override void Validate() { _ = this.EncryptedContent; @@ -151,6 +64,9 @@ public BetaWebSearchResultBlock() this.Type = JsonSerializer.Deserialize("\"web_search_result\""); } + public BetaWebSearchResultBlock(BetaWebSearchResultBlock betaWebSearchResultBlock) + : base(betaWebSearchResultBlock) { } + public BetaWebSearchResultBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -166,6 +82,7 @@ public BetaWebSearchResultBlock(IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static BetaWebSearchResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -176,6 +93,7 @@ IReadOnlyDictionary rawData class BetaWebSearchResultBlockFromRaw : IFromRaw { + /// public BetaWebSearchResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaWebSearchResultBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebSearchResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaWebSearchResultBlockParam.cs index 296f024b..1c47134b 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebSearchResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebSearchResultBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,121 +15,35 @@ public sealed record class BetaWebSearchResultBlockParam : ModelBase { public required string EncryptedContent { - get - { - if (!this._rawData.TryGetValue("encrypted_content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'encrypted_content' cannot be null", - new ArgumentOutOfRangeException( - "encrypted_content", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'encrypted_content' cannot be null", - new ArgumentNullException("encrypted_content") - ); - } - init - { - this._rawData["encrypted_content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "encrypted_content"); } + init { ModelBase.Set(this._rawData, "encrypted_content", value); } } public required string Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'title' cannot be null", - new ArgumentOutOfRangeException("title", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'title' cannot be null", - new ArgumentNullException("title") - ); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required string URL { - get - { - if (!this._rawData.TryGetValue("url", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentOutOfRangeException("url", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentNullException("url") - ); - } - init - { - this._rawData["url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "url"); } + init { ModelBase.Set(this._rawData, "url", value); } } public string? PageAge { - get - { - if (!this._rawData.TryGetValue("page_age", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["page_age"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "page_age"); } + init { ModelBase.Set(this._rawData, "page_age", value); } } + /// public override void Validate() { _ = this.EncryptedContent; @@ -153,6 +66,11 @@ public BetaWebSearchResultBlockParam() this.Type = JsonSerializer.Deserialize("\"web_search_result\""); } + public BetaWebSearchResultBlockParam( + BetaWebSearchResultBlockParam betaWebSearchResultBlockParam + ) + : base(betaWebSearchResultBlockParam) { } + public BetaWebSearchResultBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -168,6 +86,7 @@ public BetaWebSearchResultBlockParam(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaWebSearchResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -178,6 +97,7 @@ IReadOnlyDictionary rawData class BetaWebSearchResultBlockParamFromRaw : IFromRaw { + /// public BetaWebSearchResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaWebSearchResultBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebSearchTool20250305.cs b/src/Anthropic/Models/Beta/Messages/BetaWebSearchTool20250305.cs index 10c235b5..c078b380 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebSearchTool20250305.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebSearchTool20250305.cs @@ -19,57 +19,23 @@ public sealed record class BetaWebSearchTool20250305 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } - public IReadOnlyList>? AllowedCallers + public IReadOnlyList>? AllowedCallers { get { - if (!this._rawData.TryGetValue("allowed_callers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + List> + >(this.RawData, "allowed_callers"); } init { @@ -78,10 +44,7 @@ public IReadOnlyList>? AllowedCallers return; } - this._rawData["allowed_callers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "allowed_callers", value); } } @@ -91,20 +54,8 @@ public IReadOnlyList>? AllowedCallers /// public IReadOnlyList? AllowedDomains { - get - { - if (!this._rawData.TryGetValue("allowed_domains", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["allowed_domains"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "allowed_domains"); } + init { ModelBase.Set(this._rawData, "allowed_domains", value); } } /// @@ -112,20 +63,8 @@ public IReadOnlyList? AllowedDomains /// public IReadOnlyList? BlockedDomains { - get - { - if (!this._rawData.TryGetValue("blocked_domains", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["blocked_domains"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "blocked_domains"); } + init { ModelBase.Set(this._rawData, "blocked_domains", value); } } /// @@ -135,21 +74,12 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -158,13 +88,7 @@ public BetaCacheControlEphemeral? CacheControl /// public bool? DeferLoading { - get - { - if (!this._rawData.TryGetValue("defer_loading", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "defer_loading"); } init { if (value == null) @@ -172,10 +96,7 @@ public bool? DeferLoading return; } - this._rawData["defer_loading"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "defer_loading", value); } } @@ -184,31 +105,13 @@ public bool? DeferLoading /// public long? MaxUses { - get - { - if (!this._rawData.TryGetValue("max_uses", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["max_uses"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "max_uses"); } + init { ModelBase.Set(this._rawData, "max_uses", value); } } public bool? Strict { - get - { - if (!this._rawData.TryGetValue("strict", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "strict"); } init { if (value == null) @@ -216,10 +119,7 @@ public bool? Strict return; } - this._rawData["strict"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "strict", value); } } @@ -228,22 +128,11 @@ public bool? Strict /// public UserLocation? UserLocation { - get - { - if (!this._rawData.TryGetValue("user_location", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["user_location"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "user_location"); } + init { ModelBase.Set(this._rawData, "user_location", value); } } + /// public override void Validate() { if ( @@ -283,6 +172,9 @@ public BetaWebSearchTool20250305() this.Type = JsonSerializer.Deserialize("\"web_search_20250305\""); } + public BetaWebSearchTool20250305(BetaWebSearchTool20250305 betaWebSearchTool20250305) + : base(betaWebSearchTool20250305) { } + public BetaWebSearchTool20250305(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -299,6 +191,7 @@ public BetaWebSearchTool20250305(IReadOnlyDictionary rawDat } #pragma warning restore CS8618 + /// public static BetaWebSearchTool20250305 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -309,21 +202,23 @@ IReadOnlyDictionary rawData class BetaWebSearchTool20250305FromRaw : IFromRaw { + /// public BetaWebSearchTool20250305 FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaWebSearchTool20250305.FromRawUnchecked(rawData); } -[JsonConverter(typeof(AllowedCaller15Converter))] -public enum AllowedCaller15 +[JsonConverter(typeof(BetaWebSearchTool20250305AllowedCallerConverter))] +public enum BetaWebSearchTool20250305AllowedCaller { Direct, CodeExecution20250825, } -sealed class AllowedCaller15Converter : JsonConverter +sealed class BetaWebSearchTool20250305AllowedCallerConverter + : JsonConverter { - public override AllowedCaller15 Read( + public override BetaWebSearchTool20250305AllowedCaller Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -331,15 +226,16 @@ JsonSerializerOptions options { return JsonSerializer.Deserialize(ref reader, options) switch { - "direct" => AllowedCaller15.Direct, - "code_execution_20250825" => AllowedCaller15.CodeExecution20250825, - _ => (AllowedCaller15)(-1), + "direct" => BetaWebSearchTool20250305AllowedCaller.Direct, + "code_execution_20250825" => + BetaWebSearchTool20250305AllowedCaller.CodeExecution20250825, + _ => (BetaWebSearchTool20250305AllowedCaller)(-1), }; } public override void Write( Utf8JsonWriter writer, - AllowedCaller15 value, + BetaWebSearchTool20250305AllowedCaller value, JsonSerializerOptions options ) { @@ -347,8 +243,9 @@ JsonSerializerOptions options writer, value switch { - AllowedCaller15.Direct => "direct", - AllowedCaller15.CodeExecution20250825 => "code_execution_20250825", + BetaWebSearchTool20250305AllowedCaller.Direct => "direct", + BetaWebSearchTool20250305AllowedCaller.CodeExecution20250825 => + "code_execution_20250825", _ => throw new AnthropicInvalidDataException( string.Format("Invalid value '{0}' in {1}", value, nameof(value)) ), @@ -366,23 +263,8 @@ public sealed record class UserLocation : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -390,20 +272,8 @@ public JsonElement Type /// public string? City { - get - { - if (!this._rawData.TryGetValue("city", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["city"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "city"); } + init { ModelBase.Set(this._rawData, "city", value); } } /// @@ -412,20 +282,8 @@ public string? City /// public string? Country { - get - { - if (!this._rawData.TryGetValue("country", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["country"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "country"); } + init { ModelBase.Set(this._rawData, "country", value); } } /// @@ -433,20 +291,8 @@ public string? Country /// public string? Region { - get - { - if (!this._rawData.TryGetValue("region", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["region"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "region"); } + init { ModelBase.Set(this._rawData, "region", value); } } /// @@ -454,22 +300,11 @@ public string? Region /// public string? Timezone { - get - { - if (!this._rawData.TryGetValue("timezone", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["timezone"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "timezone"); } + init { ModelBase.Set(this._rawData, "timezone", value); } } + /// public override void Validate() { if ( @@ -492,6 +327,9 @@ public UserLocation() this.Type = JsonSerializer.Deserialize("\"approximate\""); } + public UserLocation(UserLocation userLocation) + : base(userLocation) { } + public UserLocation(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -507,6 +345,7 @@ public UserLocation(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static UserLocation FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -515,6 +354,7 @@ public static UserLocation FromRawUnchecked(IReadOnlyDictionary { + /// public UserLocation FromRawUnchecked(IReadOnlyDictionary rawData) => UserLocation.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolRequestError.cs b/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolRequestError.cs index f4aa08c8..854860d7 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolRequestError.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolRequestError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -18,47 +17,21 @@ public required ApiEnum ErrorCode { get { - if (!this._rawData.TryGetValue("error_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error_code' cannot be null", - new ArgumentOutOfRangeException("error_code", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["error_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "error_code" ); } + init { ModelBase.Set(this._rawData, "error_code", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.ErrorCode.Validate(); @@ -78,6 +51,11 @@ public BetaWebSearchToolRequestError() this.Type = JsonSerializer.Deserialize("\"web_search_tool_result_error\""); } + public BetaWebSearchToolRequestError( + BetaWebSearchToolRequestError betaWebSearchToolRequestError + ) + : base(betaWebSearchToolRequestError) { } + public BetaWebSearchToolRequestError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -93,6 +71,7 @@ public BetaWebSearchToolRequestError(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static BetaWebSearchToolRequestError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -112,6 +91,7 @@ ApiEnum errorCode class BetaWebSearchToolRequestErrorFromRaw : IFromRaw { + /// public BetaWebSearchToolRequestError FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaWebSearchToolRequestError.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlock.cs b/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlock.cs index 43010d67..0b252a0f 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlock.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -18,76 +17,27 @@ public required BetaWebSearchToolResultBlockContent Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new ArgumentOutOfRangeException("tool_use_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -108,6 +58,9 @@ public BetaWebSearchToolResultBlock() this.Type = JsonSerializer.Deserialize("\"web_search_tool_result\""); } + public BetaWebSearchToolResultBlock(BetaWebSearchToolResultBlock betaWebSearchToolResultBlock) + : base(betaWebSearchToolResultBlock) { } + public BetaWebSearchToolResultBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -123,6 +76,7 @@ public BetaWebSearchToolResultBlock(IReadOnlyDictionary raw } #pragma warning restore CS8618 + /// public static BetaWebSearchToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -133,6 +87,7 @@ IReadOnlyDictionary rawData class BetaWebSearchToolResultBlockFromRaw : IFromRaw { + /// public BetaWebSearchToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaWebSearchToolResultBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlockContent.cs b/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlockContent.cs index e64f2e8e..b6e223b5 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlockContent.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlockContent.cs @@ -43,12 +43,42 @@ public BetaWebSearchToolResultBlockContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickError(out var value)) { + /// // `value` is of type `BetaWebSearchToolResultError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickError([NotNullWhen(true)] out BetaWebSearchToolResultError? value) { value = this.Value as BetaWebSearchToolResultError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaWebSearchResultBlocks(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaWebSearchResultBlocks( [NotNullWhen(true)] out IReadOnlyList? value ) @@ -57,6 +87,26 @@ public bool TryPickBetaWebSearchResultBlocks( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaWebSearchToolResultError value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action error, System::Action> betaWebSearchResultBlocks @@ -77,6 +127,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaWebSearchToolResultError value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match( System::Func error, System::Func, T> betaWebSearchResultBlocks @@ -100,6 +171,16 @@ public static implicit operator BetaWebSearchToolResultBlockContent( List value ) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -108,6 +189,17 @@ public void Validate() "Data did not match any variant of BetaWebSearchToolResultBlockContent" ); } + this.Switch((error) => error.Validate(), (_) => { }); + } + + public virtual bool Equals(BetaWebSearchToolResultBlockContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlockParam.cs b/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlockParam.cs index bd20494c..54102c65 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlockParam.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -21,74 +20,24 @@ public required BetaWebSearchToolResultBlockParamContent Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new ArgumentOutOfRangeException("tool_use_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -98,23 +47,15 @@ public BetaCacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawData, + "cache_control" ); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -136,6 +77,11 @@ public BetaWebSearchToolResultBlockParam() this.Type = JsonSerializer.Deserialize("\"web_search_tool_result\""); } + public BetaWebSearchToolResultBlockParam( + BetaWebSearchToolResultBlockParam betaWebSearchToolResultBlockParam + ) + : base(betaWebSearchToolResultBlockParam) { } + public BetaWebSearchToolResultBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -151,6 +97,7 @@ public BetaWebSearchToolResultBlockParam(IReadOnlyDictionary public static BetaWebSearchToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -161,6 +108,7 @@ IReadOnlyDictionary rawData class BetaWebSearchToolResultBlockParamFromRaw : IFromRaw { + /// public BetaWebSearchToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaWebSearchToolResultBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlockParamContent.cs b/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlockParamContent.cs index c0c682a2..f0b76edd 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlockParamContent.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultBlockParamContent.cs @@ -43,6 +43,21 @@ public BetaWebSearchToolResultBlockParamContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickResultBlock(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickResultBlock( [NotNullWhen(true)] out IReadOnlyList? value ) @@ -51,12 +66,47 @@ public bool TryPickResultBlock( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickRequestError(out var value)) { + /// // `value` is of type `BetaWebSearchToolRequestError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickRequestError([NotNullWhen(true)] out BetaWebSearchToolRequestError? value) { value = this.Value as BetaWebSearchToolRequestError; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (IReadOnlyList value) => {...}, + /// (BetaWebSearchToolRequestError value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action> resultBlock, System::Action requestError @@ -77,6 +127,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (IReadOnlyList value) => {...}, + /// (BetaWebSearchToolRequestError value) => {...} + /// ); + /// + /// + /// public T Match( System::Func, T> resultBlock, System::Func requestError @@ -100,6 +171,16 @@ public static implicit operator BetaWebSearchToolResultBlockParamContent( BetaWebSearchToolRequestError value ) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -108,6 +189,17 @@ public void Validate() "Data did not match any variant of BetaWebSearchToolResultBlockParamContent" ); } + this.Switch((_) => { }, (requestError) => requestError.Validate()); + } + + public virtual bool Equals(BetaWebSearchToolResultBlockParamContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultError.cs b/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultError.cs index 6947480c..8e384bb5 100644 --- a/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultError.cs +++ b/src/Anthropic/Models/Beta/Messages/BetaWebSearchToolResultError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -18,47 +17,21 @@ public required ApiEnum ErrorCode { get { - if (!this._rawData.TryGetValue("error_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error_code' cannot be null", - new ArgumentOutOfRangeException("error_code", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["error_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "error_code" ); } + init { ModelBase.Set(this._rawData, "error_code", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.ErrorCode.Validate(); @@ -78,6 +51,9 @@ public BetaWebSearchToolResultError() this.Type = JsonSerializer.Deserialize("\"web_search_tool_result_error\""); } + public BetaWebSearchToolResultError(BetaWebSearchToolResultError betaWebSearchToolResultError) + : base(betaWebSearchToolResultError) { } + public BetaWebSearchToolResultError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -93,6 +69,7 @@ public BetaWebSearchToolResultError(IReadOnlyDictionary raw } #pragma warning restore CS8618 + /// public static BetaWebSearchToolResultError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -110,6 +87,7 @@ public BetaWebSearchToolResultError(ApiEnum { + /// public BetaWebSearchToolResultError FromRawUnchecked( IReadOnlyDictionary rawData ) => BetaWebSearchToolResultError.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Messages/MessageBetaContentBlockSourceContent.cs b/src/Anthropic/Models/Beta/Messages/MessageBetaContentBlockSourceContent.cs index ffc2dd8b..8c5cb791 100644 --- a/src/Anthropic/Models/Beta/Messages/MessageBetaContentBlockSourceContent.cs +++ b/src/Anthropic/Models/Beta/Messages/MessageBetaContentBlockSourceContent.cs @@ -51,18 +51,68 @@ public MessageBetaContentBlockSourceContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTextBlockParam(out var value)) { + /// // `value` is of type `BetaTextBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTextBlockParam([NotNullWhen(true)] out BetaTextBlockParam? value) { value = this.Value as BetaTextBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickImageBlockParam(out var value)) { + /// // `value` is of type `BetaImageBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickImageBlockParam([NotNullWhen(true)] out BetaImageBlockParam? value) { value = this.Value as BetaImageBlockParam; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaTextBlockParam value) => {...}, + /// (BetaImageBlockParam value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action textBlockParam, System::Action imageBlockParam @@ -83,6 +133,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaTextBlockParam value) => {...}, + /// (BetaImageBlockParam value) => {...} + /// ); + /// + /// + /// public T Match( System::Func textBlockParam, System::Func imageBlockParam @@ -106,6 +177,16 @@ public static implicit operator MessageBetaContentBlockSourceContent( BetaImageBlockParam value ) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -114,6 +195,20 @@ public void Validate() "Data did not match any variant of MessageBetaContentBlockSourceContent" ); } + this.Switch( + (textBlockParam) => textBlockParam.Validate(), + (imageBlockParam) => imageBlockParam.Validate() + ); + } + + public virtual bool Equals(MessageBetaContentBlockSourceContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/MessageCountTokensParams.cs b/src/Anthropic/Models/Beta/Messages/MessageCountTokensParams.cs index 17b3b832..4bf7a402 100644 --- a/src/Anthropic/Models/Beta/Messages/MessageCountTokensParams.cs +++ b/src/Anthropic/Models/Beta/Messages/MessageCountTokensParams.cs @@ -84,28 +84,9 @@ public required IReadOnlyList Messages { get { - if (!this._rawBodyData.TryGetValue("messages", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'messages' cannot be null", - new System::ArgumentOutOfRangeException("messages", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'messages' cannot be null", - new System::ArgumentNullException("messages") - ); - } - init - { - this._rawBodyData["messages"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNotNullClass>(this.RawBodyData, "messages"); } + init { ModelBase.Set(this._rawBodyData, "messages", value); } } /// @@ -116,24 +97,12 @@ public required IReadOnlyList Messages { get { - if (!this._rawBodyData.TryGetValue("model", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'model' cannot be null", - new System::ArgumentOutOfRangeException("model", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawBodyData["model"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawBodyData, + "model" ); } + init { ModelBase.Set(this._rawBodyData, "model", value); } } /// @@ -146,21 +115,12 @@ public BetaContextManagementConfig? ContextManagement { get { - if (!this._rawBodyData.TryGetValue("context_management", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawBodyData["context_management"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawBodyData, + "context_management" ); } + init { ModelBase.Set(this._rawBodyData, "context_management", value); } } /// @@ -170,12 +130,9 @@ public IReadOnlyList? MCPServers { get { - if (!this._rawBodyData.TryGetValue("mcp_servers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawBodyData, + "mcp_servers" ); } init @@ -185,10 +142,7 @@ public IReadOnlyList? MCPServers return; } - this._rawBodyData["mcp_servers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "mcp_servers", value); } } @@ -200,13 +154,7 @@ public BetaOutputConfig? OutputConfig { get { - if (!this._rawBodyData.TryGetValue("output_config", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawBodyData, "output_config"); } init { @@ -215,10 +163,7 @@ public BetaOutputConfig? OutputConfig return; } - this._rawBodyData["output_config"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "output_config", value); } } @@ -229,21 +174,12 @@ public BetaJSONOutputFormat? OutputFormat { get { - if (!this._rawBodyData.TryGetValue("output_format", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawBodyData["output_format"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawBodyData, + "output_format" ); } + init { ModelBase.Set(this._rawBodyData, "output_format", value); } } /// @@ -252,14 +188,14 @@ public BetaJSONOutputFormat? OutputFormat /// A system prompt is a way of providing context and instructions to Claude, /// such as specifying a particular goal or role. See our [guide to system prompts](https://docs.claude.com/en/docs/system-prompts). /// - public System1? System + public MessageCountTokensParamsSystem? System { get { - if (!this._rawBodyData.TryGetValue("system", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); + return ModelBase.GetNullableClass( + this.RawBodyData, + "system" + ); } init { @@ -268,10 +204,7 @@ public System1? System return; } - this._rawBodyData["system"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "system", value); } } @@ -289,12 +222,9 @@ public BetaThinkingConfigParam? Thinking { get { - if (!this._rawBodyData.TryGetValue("thinking", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawBodyData, + "thinking" ); } init @@ -304,10 +234,7 @@ public BetaThinkingConfigParam? Thinking return; } - this._rawBodyData["thinking"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "thinking", value); } } @@ -317,16 +244,7 @@ public BetaThinkingConfigParam? Thinking /// public BetaToolChoice? ToolChoice { - get - { - if (!this._rawBodyData.TryGetValue("tool_choice", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawBodyData, "tool_choice"); } init { if (value == null) @@ -334,10 +252,7 @@ public BetaToolChoice? ToolChoice return; } - this._rawBodyData["tool_choice"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "tool_choice", value); } } @@ -390,13 +305,7 @@ public BetaToolChoice? ToolChoice /// public IReadOnlyList? Tools { - get - { - if (!this._rawBodyData.TryGetValue("tools", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass>(this.RawBodyData, "tools"); } init { if (value == null) @@ -404,10 +313,7 @@ public IReadOnlyList? Tools return; } - this._rawBodyData["tools"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "tools", value); } } @@ -418,12 +324,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -433,15 +336,18 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public MessageCountTokensParams() { } + public MessageCountTokensParams(MessageCountTokensParams messageCountTokensParams) + : base(messageCountTokensParams) + { + this._rawBodyData = [.. messageCountTokensParams._rawBodyData]; + } + public MessageCountTokensParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, @@ -467,6 +373,7 @@ FrozenDictionary rawBodyData } #pragma warning restore CS8618 + /// public static MessageCountTokensParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, @@ -511,8 +418,8 @@ internal override void AddHeadersToRequest(HttpRequestMessage request, ClientOpt /// A system prompt is a way of providing context and instructions to Claude, /// such as specifying a particular goal or role. See our [guide to system prompts](https://docs.claude.com/en/docs/system-prompts). /// -[JsonConverter(typeof(System1Converter))] -public record class System1 +[JsonConverter(typeof(MessageCountTokensParamsSystemConverter))] +public record class MessageCountTokensParamsSystem { public object? Value { get; } = null; @@ -523,29 +430,62 @@ public JsonElement Json get { return this._json ??= JsonSerializer.SerializeToElement(this.Value); } } - public System1(string value, JsonElement? json = null) + public MessageCountTokensParamsSystem(string value, JsonElement? json = null) { this.Value = value; this._json = json; } - public System1(IReadOnlyList value, JsonElement? json = null) + public MessageCountTokensParamsSystem( + IReadOnlyList value, + JsonElement? json = null + ) { this.Value = ImmutableArray.ToImmutableArray(value); this._json = json; } - public System1(JsonElement json) + public MessageCountTokensParamsSystem(JsonElement json) { this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaTextBlockParams(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaTextBlockParams( [NotNullWhen(true)] out IReadOnlyList? value ) @@ -554,6 +494,26 @@ public bool TryPickBetaTextBlockParams( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action @string, System::Action> betaTextBlockParams @@ -569,11 +529,32 @@ public void Switch( break; default: throw new AnthropicInvalidDataException( - "Data did not match any variant of System1" + "Data did not match any variant of MessageCountTokensParamsSystem" ); } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match( System::Func @string, System::Func, T> betaTextBlockParams @@ -584,28 +565,51 @@ public T Match( string value => @string(value), IReadOnlyList value => betaTextBlockParams(value), _ => throw new AnthropicInvalidDataException( - "Data did not match any variant of System1" + "Data did not match any variant of MessageCountTokensParamsSystem" ), }; } - public static implicit operator System1(string value) => new(value); + public static implicit operator MessageCountTokensParamsSystem(string value) => new(value); - public static implicit operator System1(List value) => - new((IReadOnlyList)value); + public static implicit operator MessageCountTokensParamsSystem( + List value + ) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { - throw new AnthropicInvalidDataException("Data did not match any variant of System1"); + throw new AnthropicInvalidDataException( + "Data did not match any variant of MessageCountTokensParamsSystem" + ); } } + + public virtual bool Equals(MessageCountTokensParamsSystem? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } } -sealed class System1Converter : JsonConverter +sealed class MessageCountTokensParamsSystemConverter : JsonConverter { - public override System1? Read( + public override MessageCountTokensParamsSystem? Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -641,7 +645,11 @@ JsonSerializerOptions options return new(json); } - public override void Write(Utf8JsonWriter writer, System1 value, JsonSerializerOptions options) + public override void Write( + Utf8JsonWriter writer, + MessageCountTokensParamsSystem value, + JsonSerializerOptions options + ) { JsonSerializer.Serialize(writer, value.Json, options); } @@ -967,24 +975,84 @@ public Tool(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBeta(out var value)) { + /// // `value` is of type `BetaTool` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBeta([NotNullWhen(true)] out BetaTool? value) { value = this.Value as BetaTool; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolBash20241022(out var value)) { + /// // `value` is of type `BetaToolBash20241022` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolBash20241022([NotNullWhen(true)] out BetaToolBash20241022? value) { value = this.Value as BetaToolBash20241022; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolBash20250124(out var value)) { + /// // `value` is of type `BetaToolBash20250124` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolBash20250124([NotNullWhen(true)] out BetaToolBash20250124? value) { value = this.Value as BetaToolBash20250124; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaCodeExecutionTool20250522(out var value)) { + /// // `value` is of type `BetaCodeExecutionTool20250522` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaCodeExecutionTool20250522( [NotNullWhen(true)] out BetaCodeExecutionTool20250522? value ) @@ -993,6 +1061,21 @@ public bool TryPickBetaCodeExecutionTool20250522( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaCodeExecutionTool20250825(out var value)) { + /// // `value` is of type `BetaCodeExecutionTool20250825` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaCodeExecutionTool20250825( [NotNullWhen(true)] out BetaCodeExecutionTool20250825? value ) @@ -1001,6 +1084,21 @@ public bool TryPickBetaCodeExecutionTool20250825( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolComputerUse20241022(out var value)) { + /// // `value` is of type `BetaToolComputerUse20241022` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolComputerUse20241022( [NotNullWhen(true)] out BetaToolComputerUse20241022? value ) @@ -1009,12 +1107,42 @@ public bool TryPickBetaToolComputerUse20241022( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaMemoryTool20250818(out var value)) { + /// // `value` is of type `BetaMemoryTool20250818` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaMemoryTool20250818([NotNullWhen(true)] out BetaMemoryTool20250818? value) { value = this.Value as BetaMemoryTool20250818; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolComputerUse20250124(out var value)) { + /// // `value` is of type `BetaToolComputerUse20250124` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolComputerUse20250124( [NotNullWhen(true)] out BetaToolComputerUse20250124? value ) @@ -1023,6 +1151,21 @@ public bool TryPickBetaToolComputerUse20250124( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolTextEditor20241022(out var value)) { + /// // `value` is of type `BetaToolTextEditor20241022` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolTextEditor20241022( [NotNullWhen(true)] out BetaToolTextEditor20241022? value ) @@ -1031,6 +1174,21 @@ public bool TryPickBetaToolTextEditor20241022( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolComputerUse20251124(out var value)) { + /// // `value` is of type `BetaToolComputerUse20251124` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolComputerUse20251124( [NotNullWhen(true)] out BetaToolComputerUse20251124? value ) @@ -1039,6 +1197,21 @@ public bool TryPickBetaToolComputerUse20251124( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolTextEditor20250124(out var value)) { + /// // `value` is of type `BetaToolTextEditor20250124` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolTextEditor20250124( [NotNullWhen(true)] out BetaToolTextEditor20250124? value ) @@ -1047,6 +1220,21 @@ public bool TryPickBetaToolTextEditor20250124( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolTextEditor20250429(out var value)) { + /// // `value` is of type `BetaToolTextEditor20250429` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolTextEditor20250429( [NotNullWhen(true)] out BetaToolTextEditor20250429? value ) @@ -1055,6 +1243,21 @@ public bool TryPickBetaToolTextEditor20250429( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolTextEditor20250728(out var value)) { + /// // `value` is of type `BetaToolTextEditor20250728` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolTextEditor20250728( [NotNullWhen(true)] out BetaToolTextEditor20250728? value ) @@ -1063,6 +1266,21 @@ public bool TryPickBetaToolTextEditor20250728( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaWebSearchTool20250305(out var value)) { + /// // `value` is of type `BetaWebSearchTool20250305` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaWebSearchTool20250305( [NotNullWhen(true)] out BetaWebSearchTool20250305? value ) @@ -1071,6 +1289,21 @@ public bool TryPickBetaWebSearchTool20250305( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaWebFetchTool20250910(out var value)) { + /// // `value` is of type `BetaWebFetchTool20250910` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaWebFetchTool20250910( [NotNullWhen(true)] out BetaWebFetchTool20250910? value ) @@ -1079,6 +1312,21 @@ public bool TryPickBetaWebFetchTool20250910( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolSearchToolBm25_20251119(out var value)) { + /// // `value` is of type `BetaToolSearchToolBm25_20251119` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolSearchToolBm25_20251119( [NotNullWhen(true)] out BetaToolSearchToolBm25_20251119? value ) @@ -1087,6 +1335,21 @@ public bool TryPickBetaToolSearchToolBm25_20251119( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaToolSearchToolRegex20251119(out var value)) { + /// // `value` is of type `BetaToolSearchToolRegex20251119` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaToolSearchToolRegex20251119( [NotNullWhen(true)] out BetaToolSearchToolRegex20251119? value ) @@ -1095,12 +1358,63 @@ public bool TryPickBetaToolSearchToolRegex20251119( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaMCPToolset(out var value)) { + /// // `value` is of type `BetaMCPToolset` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaMCPToolset([NotNullWhen(true)] out BetaMCPToolset? value) { value = this.Value as BetaMCPToolset; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaTool value) => {...}, + /// (BetaToolBash20241022 value) => {...}, + /// (BetaToolBash20250124 value) => {...}, + /// (BetaCodeExecutionTool20250522 value) => {...}, + /// (BetaCodeExecutionTool20250825 value) => {...}, + /// (BetaToolComputerUse20241022 value) => {...}, + /// (BetaMemoryTool20250818 value) => {...}, + /// (BetaToolComputerUse20250124 value) => {...}, + /// (BetaToolTextEditor20241022 value) => {...}, + /// (BetaToolComputerUse20251124 value) => {...}, + /// (BetaToolTextEditor20250124 value) => {...}, + /// (BetaToolTextEditor20250429 value) => {...}, + /// (BetaToolTextEditor20250728 value) => {...}, + /// (BetaWebSearchTool20250305 value) => {...}, + /// (BetaWebFetchTool20250910 value) => {...}, + /// (BetaToolSearchToolBm25_20251119 value) => {...}, + /// (BetaToolSearchToolRegex20251119 value) => {...}, + /// (BetaMCPToolset value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action beta, System::Action betaToolBash20241022, @@ -1183,6 +1497,43 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaTool value) => {...}, + /// (BetaToolBash20241022 value) => {...}, + /// (BetaToolBash20250124 value) => {...}, + /// (BetaCodeExecutionTool20250522 value) => {...}, + /// (BetaCodeExecutionTool20250825 value) => {...}, + /// (BetaToolComputerUse20241022 value) => {...}, + /// (BetaMemoryTool20250818 value) => {...}, + /// (BetaToolComputerUse20250124 value) => {...}, + /// (BetaToolTextEditor20241022 value) => {...}, + /// (BetaToolComputerUse20251124 value) => {...}, + /// (BetaToolTextEditor20250124 value) => {...}, + /// (BetaToolTextEditor20250429 value) => {...}, + /// (BetaToolTextEditor20250728 value) => {...}, + /// (BetaWebSearchTool20250305 value) => {...}, + /// (BetaWebFetchTool20250910 value) => {...}, + /// (BetaToolSearchToolBm25_20251119 value) => {...}, + /// (BetaToolSearchToolRegex20251119 value) => {...}, + /// (BetaMCPToolset value) => {...} + /// ); + /// + /// + /// public T Match( System::Func beta, System::Func betaToolBash20241022, @@ -1264,12 +1615,52 @@ public T Match( public static implicit operator Tool(BetaMCPToolset value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of Tool"); } + this.Switch( + (beta) => beta.Validate(), + (betaToolBash20241022) => betaToolBash20241022.Validate(), + (betaToolBash20250124) => betaToolBash20250124.Validate(), + (betaCodeExecutionTool20250522) => betaCodeExecutionTool20250522.Validate(), + (betaCodeExecutionTool20250825) => betaCodeExecutionTool20250825.Validate(), + (betaToolComputerUse20241022) => betaToolComputerUse20241022.Validate(), + (betaMemoryTool20250818) => betaMemoryTool20250818.Validate(), + (betaToolComputerUse20250124) => betaToolComputerUse20250124.Validate(), + (betaToolTextEditor20241022) => betaToolTextEditor20241022.Validate(), + (betaToolComputerUse20251124) => betaToolComputerUse20251124.Validate(), + (betaToolTextEditor20250124) => betaToolTextEditor20250124.Validate(), + (betaToolTextEditor20250429) => betaToolTextEditor20250429.Validate(), + (betaToolTextEditor20250728) => betaToolTextEditor20250728.Validate(), + (betaWebSearchTool20250305) => betaWebSearchTool20250305.Validate(), + (betaWebFetchTool20250910) => betaWebFetchTool20250910.Validate(), + (betaToolSearchToolBm25_20251119) => betaToolSearchToolBm25_20251119.Validate(), + (betaToolSearchToolRegex20251119) => betaToolSearchToolRegex20251119.Validate(), + (betaMCPToolset) => betaMCPToolset.Validate() + ); + } + + public virtual bool Equals(Tool? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Beta/Messages/MessageCreateParams.cs b/src/Anthropic/Models/Beta/Messages/MessageCreateParams.cs index caaff0c0..e753afd1 100644 --- a/src/Anthropic/Models/Beta/Messages/MessageCreateParams.cs +++ b/src/Anthropic/Models/Beta/Messages/MessageCreateParams.cs @@ -40,26 +40,8 @@ public IReadOnlyDictionary RawBodyData /// public required long MaxTokens { - get - { - if (!this._rawBodyData.TryGetValue("max_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'max_tokens' cannot be null", - new System::ArgumentOutOfRangeException( - "max_tokens", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawBodyData["max_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawBodyData, "max_tokens"); } + init { ModelBase.Set(this._rawBodyData, "max_tokens", value); } } /// @@ -117,28 +99,9 @@ public required IReadOnlyList Messages { get { - if (!this._rawBodyData.TryGetValue("messages", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'messages' cannot be null", - new System::ArgumentOutOfRangeException("messages", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'messages' cannot be null", - new System::ArgumentNullException("messages") - ); - } - init - { - this._rawBodyData["messages"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNotNullClass>(this.RawBodyData, "messages"); } + init { ModelBase.Set(this._rawBodyData, "messages", value); } } /// @@ -149,24 +112,12 @@ public required IReadOnlyList Messages { get { - if (!this._rawBodyData.TryGetValue("model", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'model' cannot be null", - new System::ArgumentOutOfRangeException("model", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawBodyData["model"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawBodyData, + "model" ); } + init { ModelBase.Set(this._rawBodyData, "model", value); } } /// @@ -174,20 +125,8 @@ public required IReadOnlyList Messages /// public Container? Container { - get - { - if (!this._rawBodyData.TryGetValue("container", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawBodyData["container"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawBodyData, "container"); } + init { ModelBase.Set(this._rawBodyData, "container", value); } } /// @@ -200,21 +139,12 @@ public BetaContextManagementConfig? ContextManagement { get { - if (!this._rawBodyData.TryGetValue("context_management", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawBodyData["context_management"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawBodyData, + "context_management" ); } + init { ModelBase.Set(this._rawBodyData, "context_management", value); } } /// @@ -224,12 +154,9 @@ public IReadOnlyList? MCPServers { get { - if (!this._rawBodyData.TryGetValue("mcp_servers", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawBodyData, + "mcp_servers" ); } init @@ -239,10 +166,7 @@ public IReadOnlyList? MCPServers return; } - this._rawBodyData["mcp_servers"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "mcp_servers", value); } } @@ -251,13 +175,7 @@ public IReadOnlyList? MCPServers /// public BetaMetadata? Metadata { - get - { - if (!this._rawBodyData.TryGetValue("metadata", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawBodyData, "metadata"); } init { if (value == null) @@ -265,10 +183,7 @@ public BetaMetadata? Metadata return; } - this._rawBodyData["metadata"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "metadata", value); } } @@ -280,13 +195,7 @@ public BetaOutputConfig? OutputConfig { get { - if (!this._rawBodyData.TryGetValue("output_config", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawBodyData, "output_config"); } init { @@ -295,10 +204,7 @@ public BetaOutputConfig? OutputConfig return; } - this._rawBodyData["output_config"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "output_config", value); } } @@ -309,21 +215,12 @@ public BetaJSONOutputFormat? OutputFormat { get { - if (!this._rawBodyData.TryGetValue("output_format", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawBodyData["output_format"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawBodyData, + "output_format" ); } + init { ModelBase.Set(this._rawBodyData, "output_format", value); } } /// @@ -337,12 +234,9 @@ public ApiEnum? ServiceTier { get { - if (!this._rawBodyData.TryGetValue("service_tier", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawBodyData, + "service_tier" ); } init @@ -352,10 +246,7 @@ public ApiEnum? ServiceTier return; } - this._rawBodyData["service_tier"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "service_tier", value); } } @@ -373,13 +264,7 @@ public ApiEnum? ServiceTier /// public IReadOnlyList? StopSequences { - get - { - if (!this._rawBodyData.TryGetValue("stop_sequences", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass>(this.RawBodyData, "stop_sequences"); } init { if (value == null) @@ -387,10 +272,7 @@ public IReadOnlyList? StopSequences return; } - this._rawBodyData["stop_sequences"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "stop_sequences", value); } } @@ -400,14 +282,14 @@ public IReadOnlyList? StopSequences /// A system prompt is a way of providing context and instructions to Claude, /// such as specifying a particular goal or role. See our [guide to system prompts](https://docs.claude.com/en/docs/system-prompts). /// - public SystemModel? System + public MessageCreateParamsSystem? System { get { - if (!this._rawBodyData.TryGetValue("system", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); + return ModelBase.GetNullableClass( + this.RawBodyData, + "system" + ); } init { @@ -416,10 +298,7 @@ public SystemModel? System return; } - this._rawBodyData["system"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "system", value); } } @@ -435,13 +314,7 @@ public SystemModel? System /// public double? Temperature { - get - { - if (!this._rawBodyData.TryGetValue("temperature", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawBodyData, "temperature"); } init { if (value == null) @@ -449,10 +322,7 @@ public double? Temperature return; } - this._rawBodyData["temperature"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "temperature", value); } } @@ -470,12 +340,9 @@ public BetaThinkingConfigParam? Thinking { get { - if (!this._rawBodyData.TryGetValue("thinking", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass( + this.RawBodyData, + "thinking" ); } init @@ -485,10 +352,7 @@ public BetaThinkingConfigParam? Thinking return; } - this._rawBodyData["thinking"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "thinking", value); } } @@ -498,16 +362,7 @@ public BetaThinkingConfigParam? Thinking /// public BetaToolChoice? ToolChoice { - get - { - if (!this._rawBodyData.TryGetValue("tool_choice", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawBodyData, "tool_choice"); } init { if (value == null) @@ -515,10 +370,7 @@ public BetaToolChoice? ToolChoice return; } - this._rawBodyData["tool_choice"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "tool_choice", value); } } @@ -571,16 +423,7 @@ public BetaToolChoice? ToolChoice /// public IReadOnlyList? Tools { - get - { - if (!this._rawBodyData.TryGetValue("tools", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawBodyData, "tools"); } init { if (value == null) @@ -588,10 +431,7 @@ public IReadOnlyList? Tools return; } - this._rawBodyData["tools"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "tools", value); } } @@ -605,13 +445,7 @@ public IReadOnlyList? Tools /// public long? TopK { - get - { - if (!this._rawBodyData.TryGetValue("top_k", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawBodyData, "top_k"); } init { if (value == null) @@ -619,10 +453,7 @@ public long? TopK return; } - this._rawBodyData["top_k"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "top_k", value); } } @@ -638,13 +469,7 @@ public long? TopK /// public double? TopP { - get - { - if (!this._rawBodyData.TryGetValue("top_p", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawBodyData, "top_p"); } init { if (value == null) @@ -652,10 +477,7 @@ public double? TopP return; } - this._rawBodyData["top_p"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "top_p", value); } } @@ -666,12 +488,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -681,15 +500,18 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public MessageCreateParams() { } + public MessageCreateParams(MessageCreateParams messageCreateParams) + : base(messageCreateParams) + { + this._rawBodyData = [.. messageCreateParams._rawBodyData]; + } + public MessageCreateParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, @@ -715,6 +537,7 @@ FrozenDictionary rawBodyData } #pragma warning restore CS8618 + /// public static MessageCreateParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, @@ -785,18 +608,68 @@ public Container(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaContainerParams(out var value)) { + /// // `value` is of type `BetaContainerParams` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaContainerParams([NotNullWhen(true)] out BetaContainerParams? value) { value = this.Value as BetaContainerParams; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (BetaContainerParams value) => {...}, + /// (string value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action betaContainerParams, System::Action @string @@ -817,6 +690,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (BetaContainerParams value) => {...}, + /// (string value) => {...} + /// ); + /// + /// + /// public T Match( System::Func betaContainerParams, System::Func @string @@ -836,12 +730,33 @@ public T Match( public static implicit operator Container(string value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of Container"); } + this.Switch((betaContainerParams) => betaContainerParams.Validate(), (_) => { }); + } + + public virtual bool Equals(Container? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } @@ -951,8 +866,8 @@ JsonSerializerOptions options /// A system prompt is a way of providing context and instructions to Claude, /// such as specifying a particular goal or role. See our [guide to system prompts](https://docs.claude.com/en/docs/system-prompts). /// -[JsonConverter(typeof(SystemModelConverter))] -public record class SystemModel +[JsonConverter(typeof(MessageCreateParamsSystemConverter))] +public record class MessageCreateParamsSystem { public object? Value { get; } = null; @@ -963,29 +878,62 @@ public JsonElement Json get { return this._json ??= JsonSerializer.SerializeToElement(this.Value); } } - public SystemModel(string value, JsonElement? json = null) + public MessageCreateParamsSystem(string value, JsonElement? json = null) { this.Value = value; this._json = json; } - public SystemModel(IReadOnlyList value, JsonElement? json = null) + public MessageCreateParamsSystem( + IReadOnlyList value, + JsonElement? json = null + ) { this.Value = ImmutableArray.ToImmutableArray(value); this._json = json; } - public SystemModel(JsonElement json) + public MessageCreateParamsSystem(JsonElement json) { this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBetaTextBlockParams(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBetaTextBlockParams( [NotNullWhen(true)] out IReadOnlyList? value ) @@ -994,6 +942,26 @@ public bool TryPickBetaTextBlockParams( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action @string, System::Action> betaTextBlockParams @@ -1009,11 +977,32 @@ public void Switch( break; default: throw new AnthropicInvalidDataException( - "Data did not match any variant of SystemModel" + "Data did not match any variant of MessageCreateParamsSystem" ); } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match( System::Func @string, System::Func, T> betaTextBlockParams @@ -1024,30 +1013,50 @@ public T Match( string value => @string(value), IReadOnlyList value => betaTextBlockParams(value), _ => throw new AnthropicInvalidDataException( - "Data did not match any variant of SystemModel" + "Data did not match any variant of MessageCreateParamsSystem" ), }; } - public static implicit operator SystemModel(string value) => new(value); + public static implicit operator MessageCreateParamsSystem(string value) => new(value); - public static implicit operator SystemModel(List value) => + public static implicit operator MessageCreateParamsSystem(List value) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException( - "Data did not match any variant of SystemModel" + "Data did not match any variant of MessageCreateParamsSystem" ); } } + + public virtual bool Equals(MessageCreateParamsSystem? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } } -sealed class SystemModelConverter : JsonConverter +sealed class MessageCreateParamsSystemConverter : JsonConverter { - public override SystemModel? Read( + public override MessageCreateParamsSystem? Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -1085,7 +1094,7 @@ JsonSerializerOptions options public override void Write( Utf8JsonWriter writer, - SystemModel value, + MessageCreateParamsSystem value, JsonSerializerOptions options ) { diff --git a/src/Anthropic/Models/Beta/Models/BetaModelInfo.cs b/src/Anthropic/Models/Beta/Models/BetaModelInfo.cs index f90b184a..0e6af309 100644 --- a/src/Anthropic/Models/Beta/Models/BetaModelInfo.cs +++ b/src/Anthropic/Models/Beta/Models/BetaModelInfo.cs @@ -17,27 +17,8 @@ public sealed record class BetaModelInfo : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -46,23 +27,8 @@ public required string ID /// public required DateTimeOffset CreatedAt { - get - { - if (!this._rawData.TryGetValue("created_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new ArgumentOutOfRangeException("created_at", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["created_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "created_at"); } + init { ModelBase.Set(this._rawData, "created_at", value); } } /// @@ -70,27 +36,8 @@ public required DateTimeOffset CreatedAt /// public required string DisplayName { - get - { - if (!this._rawData.TryGetValue("display_name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'display_name' cannot be null", - new ArgumentOutOfRangeException("display_name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'display_name' cannot be null", - new ArgumentNullException("display_name") - ); - } - init - { - this._rawData["display_name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "display_name"); } + init { ModelBase.Set(this._rawData, "display_name", value); } } /// @@ -100,25 +47,11 @@ public required string DisplayName /// public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ID; @@ -137,6 +70,9 @@ public BetaModelInfo() this.Type = JsonSerializer.Deserialize("\"model\""); } + public BetaModelInfo(BetaModelInfo betaModelInfo) + : base(betaModelInfo) { } + public BetaModelInfo(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -152,6 +88,7 @@ public BetaModelInfo(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BetaModelInfo FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -160,6 +97,7 @@ public static BetaModelInfo FromRawUnchecked(IReadOnlyDictionary { + /// public BetaModelInfo FromRawUnchecked(IReadOnlyDictionary rawData) => BetaModelInfo.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Models/ModelListPageResponse.cs b/src/Anthropic/Models/Beta/Models/ModelListPageResponse.cs index 12117c57..a388237a 100644 --- a/src/Anthropic/Models/Beta/Models/ModelListPageResponse.cs +++ b/src/Anthropic/Models/Beta/Models/ModelListPageResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Models; @@ -14,30 +12,8 @@ public sealed record class ModelListPageResponse : ModelBase { public required IReadOnlyList Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } /// @@ -45,20 +21,8 @@ public required IReadOnlyList Data /// public required string? FirstID { - get - { - if (!this._rawData.TryGetValue("first_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["first_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "first_id"); } + init { ModelBase.Set(this._rawData, "first_id", value); } } /// @@ -66,23 +30,8 @@ public required string? FirstID /// public required bool HasMore { - get - { - if (!this._rawData.TryGetValue("has_more", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'has_more' cannot be null", - new ArgumentOutOfRangeException("has_more", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["has_more"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "has_more"); } + init { ModelBase.Set(this._rawData, "has_more", value); } } /// @@ -90,22 +39,11 @@ public required bool HasMore /// public required string? LastID { - get - { - if (!this._rawData.TryGetValue("last_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["last_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "last_id"); } + init { ModelBase.Set(this._rawData, "last_id", value); } } + /// public override void Validate() { foreach (var item in this.Data) @@ -119,6 +57,9 @@ public override void Validate() public ModelListPageResponse() { } + public ModelListPageResponse(ModelListPageResponse modelListPageResponse) + : base(modelListPageResponse) { } + public ModelListPageResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -132,6 +73,7 @@ public ModelListPageResponse(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ModelListPageResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -142,6 +84,7 @@ IReadOnlyDictionary rawData class ModelListPageResponseFromRaw : IFromRaw { + /// public ModelListPageResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => ModelListPageResponse.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Models/ModelListParams.cs b/src/Anthropic/Models/Beta/Models/ModelListParams.cs index 87256e59..e97ceb8d 100644 --- a/src/Anthropic/Models/Beta/Models/ModelListParams.cs +++ b/src/Anthropic/Models/Beta/Models/ModelListParams.cs @@ -22,13 +22,7 @@ public sealed record class ModelListParams : ParamsBase /// public string? AfterID { - get - { - if (!this._rawQueryData.TryGetValue("after_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawQueryData, "after_id"); } init { if (value == null) @@ -36,10 +30,7 @@ public string? AfterID return; } - this._rawQueryData["after_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "after_id", value); } } @@ -49,13 +40,7 @@ public string? AfterID /// public string? BeforeID { - get - { - if (!this._rawQueryData.TryGetValue("before_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawQueryData, "before_id"); } init { if (value == null) @@ -63,10 +48,7 @@ public string? BeforeID return; } - this._rawQueryData["before_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "before_id", value); } } @@ -77,13 +59,7 @@ public string? BeforeID /// public long? Limit { - get - { - if (!this._rawQueryData.TryGetValue("limit", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawQueryData, "limit"); } init { if (value == null) @@ -91,10 +67,7 @@ public long? Limit return; } - this._rawQueryData["limit"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "limit", value); } } @@ -105,12 +78,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -120,15 +90,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public ModelListParams() { } + public ModelListParams(ModelListParams modelListParams) + : base(modelListParams) { } + public ModelListParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -150,6 +120,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static ModelListParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Models/ModelRetrieveParams.cs b/src/Anthropic/Models/Beta/Models/ModelRetrieveParams.cs index 53bb4557..2fbd3753 100644 --- a/src/Anthropic/Models/Beta/Models/ModelRetrieveParams.cs +++ b/src/Anthropic/Models/Beta/Models/ModelRetrieveParams.cs @@ -25,12 +25,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -40,15 +37,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public ModelRetrieveParams() { } + public ModelRetrieveParams(ModelRetrieveParams modelRetrieveParams) + : base(modelRetrieveParams) { } + public ModelRetrieveParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -70,6 +67,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static ModelRetrieveParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Skills/SkillCreateParams.cs b/src/Anthropic/Models/Beta/Skills/SkillCreateParams.cs index 6f2f4cb2..a6264d2d 100644 --- a/src/Anthropic/Models/Beta/Skills/SkillCreateParams.cs +++ b/src/Anthropic/Models/Beta/Skills/SkillCreateParams.cs @@ -29,20 +29,8 @@ public IReadOnlyDictionary RawBodyData /// public string? DisplayTitle { - get - { - if (!this._rawBodyData.TryGetValue("display_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawBodyData["display_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawBodyData, "display_title"); } + init { ModelBase.Set(this._rawBodyData, "display_title", value); } } /// @@ -53,20 +41,8 @@ public string? DisplayTitle /// public IReadOnlyList? Files { - get - { - if (!this._rawBodyData.TryGetValue("files", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } - init - { - this._rawBodyData["files"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawBodyData, "files"); } + init { ModelBase.Set(this._rawBodyData, "files", value); } } /// @@ -76,12 +52,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -91,15 +64,18 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public SkillCreateParams() { } + public SkillCreateParams(SkillCreateParams skillCreateParams) + : base(skillCreateParams) + { + this._rawBodyData = [.. skillCreateParams._rawBodyData]; + } + public SkillCreateParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, @@ -125,6 +101,7 @@ FrozenDictionary rawBodyData } #pragma warning restore CS8618 + /// public static SkillCreateParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, diff --git a/src/Anthropic/Models/Beta/Skills/SkillCreateResponse.cs b/src/Anthropic/Models/Beta/Skills/SkillCreateResponse.cs index b8cdeb71..cdf2f129 100644 --- a/src/Anthropic/Models/Beta/Skills/SkillCreateResponse.cs +++ b/src/Anthropic/Models/Beta/Skills/SkillCreateResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Skills; @@ -19,27 +17,8 @@ public sealed record class SkillCreateResponse : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -47,27 +26,8 @@ public required string ID /// public required string CreatedAt { - get - { - if (!this._rawData.TryGetValue("created_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new ArgumentOutOfRangeException("created_at", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new ArgumentNullException("created_at") - ); - } - init - { - this._rawData["created_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "created_at"); } + init { ModelBase.Set(this._rawData, "created_at", value); } } /// @@ -78,20 +38,8 @@ public required string CreatedAt /// public required string? DisplayTitle { - get - { - if (!this._rawData.TryGetValue("display_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["display_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "display_title"); } + init { ModelBase.Set(this._rawData, "display_title", value); } } /// @@ -101,20 +49,8 @@ public required string? DisplayTitle /// public required string? LatestVersion { - get - { - if (!this._rawData.TryGetValue("latest_version", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["latest_version"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "latest_version"); } + init { ModelBase.Set(this._rawData, "latest_version", value); } } /// @@ -125,27 +61,8 @@ public required string? LatestVersion /// public required string Source { - get - { - if (!this._rawData.TryGetValue("source", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentOutOfRangeException("source", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentNullException("source") - ); - } - init - { - this._rawData["source"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "source"); } + init { ModelBase.Set(this._rawData, "source", value); } } /// @@ -155,27 +72,8 @@ public required string Source /// public required string Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentNullException("type") - ); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -183,29 +81,11 @@ public required string Type /// public required string UpdatedAt { - get - { - if (!this._rawData.TryGetValue("updated_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'updated_at' cannot be null", - new ArgumentOutOfRangeException("updated_at", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'updated_at' cannot be null", - new ArgumentNullException("updated_at") - ); - } - init - { - this._rawData["updated_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "updated_at"); } + init { ModelBase.Set(this._rawData, "updated_at", value); } } + /// public override void Validate() { _ = this.ID; @@ -219,6 +99,9 @@ public override void Validate() public SkillCreateResponse() { } + public SkillCreateResponse(SkillCreateResponse skillCreateResponse) + : base(skillCreateResponse) { } + public SkillCreateResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -232,6 +115,7 @@ public SkillCreateResponse(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static SkillCreateResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -242,6 +126,7 @@ IReadOnlyDictionary rawData class SkillCreateResponseFromRaw : IFromRaw { + /// public SkillCreateResponse FromRawUnchecked(IReadOnlyDictionary rawData) => SkillCreateResponse.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Skills/SkillDeleteParams.cs b/src/Anthropic/Models/Beta/Skills/SkillDeleteParams.cs index 53d502aa..d384911f 100644 --- a/src/Anthropic/Models/Beta/Skills/SkillDeleteParams.cs +++ b/src/Anthropic/Models/Beta/Skills/SkillDeleteParams.cs @@ -23,12 +23,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -38,15 +35,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public SkillDeleteParams() { } + public SkillDeleteParams(SkillDeleteParams skillDeleteParams) + : base(skillDeleteParams) { } + public SkillDeleteParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -68,6 +65,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static SkillDeleteParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Skills/SkillDeleteResponse.cs b/src/Anthropic/Models/Beta/Skills/SkillDeleteResponse.cs index 1af88ae7..26e76dff 100644 --- a/src/Anthropic/Models/Beta/Skills/SkillDeleteResponse.cs +++ b/src/Anthropic/Models/Beta/Skills/SkillDeleteResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Skills; @@ -19,27 +17,8 @@ public sealed record class SkillDeleteResponse : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -49,29 +28,11 @@ public required string ID /// public required string Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentNullException("type") - ); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ID; @@ -80,6 +41,9 @@ public override void Validate() public SkillDeleteResponse() { } + public SkillDeleteResponse(SkillDeleteResponse skillDeleteResponse) + : base(skillDeleteResponse) { } + public SkillDeleteResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -93,6 +57,7 @@ public SkillDeleteResponse(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static SkillDeleteResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -103,6 +68,7 @@ IReadOnlyDictionary rawData class SkillDeleteResponseFromRaw : IFromRaw { + /// public SkillDeleteResponse FromRawUnchecked(IReadOnlyDictionary rawData) => SkillDeleteResponse.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Skills/SkillListPageResponse.cs b/src/Anthropic/Models/Beta/Skills/SkillListPageResponse.cs index 9bf91d6e..6bd2772b 100644 --- a/src/Anthropic/Models/Beta/Skills/SkillListPageResponse.cs +++ b/src/Anthropic/Models/Beta/Skills/SkillListPageResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Skills; @@ -17,27 +15,8 @@ public sealed record class SkillListPageResponse : ModelBase /// public required IReadOnlyList Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize>(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } /// @@ -48,23 +27,8 @@ public required IReadOnlyList Data /// public required bool HasMore { - get - { - if (!this._rawData.TryGetValue("has_more", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'has_more' cannot be null", - new ArgumentOutOfRangeException("has_more", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["has_more"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "has_more"); } + init { ModelBase.Set(this._rawData, "has_more", value); } } /// @@ -75,22 +39,11 @@ public required bool HasMore /// public required string? NextPage { - get - { - if (!this._rawData.TryGetValue("next_page", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["next_page"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "next_page"); } + init { ModelBase.Set(this._rawData, "next_page", value); } } + /// public override void Validate() { foreach (var item in this.Data) @@ -103,6 +56,9 @@ public override void Validate() public SkillListPageResponse() { } + public SkillListPageResponse(SkillListPageResponse skillListPageResponse) + : base(skillListPageResponse) { } + public SkillListPageResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -116,6 +72,7 @@ public SkillListPageResponse(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static SkillListPageResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -126,6 +83,7 @@ IReadOnlyDictionary rawData class SkillListPageResponseFromRaw : IFromRaw { + /// public SkillListPageResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => SkillListPageResponse.FromRawUnchecked(rawData); @@ -141,27 +99,8 @@ public sealed record class Data : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -169,27 +108,8 @@ public required string ID /// public required string CreatedAt { - get - { - if (!this._rawData.TryGetValue("created_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new ArgumentOutOfRangeException("created_at", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new ArgumentNullException("created_at") - ); - } - init - { - this._rawData["created_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "created_at"); } + init { ModelBase.Set(this._rawData, "created_at", value); } } /// @@ -200,20 +120,8 @@ public required string CreatedAt /// public required string? DisplayTitle { - get - { - if (!this._rawData.TryGetValue("display_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["display_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "display_title"); } + init { ModelBase.Set(this._rawData, "display_title", value); } } /// @@ -223,20 +131,8 @@ public required string? DisplayTitle /// public required string? LatestVersion { - get - { - if (!this._rawData.TryGetValue("latest_version", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["latest_version"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "latest_version"); } + init { ModelBase.Set(this._rawData, "latest_version", value); } } /// @@ -247,27 +143,8 @@ public required string? LatestVersion /// public required string Source { - get - { - if (!this._rawData.TryGetValue("source", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentOutOfRangeException("source", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentNullException("source") - ); - } - init - { - this._rawData["source"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "source"); } + init { ModelBase.Set(this._rawData, "source", value); } } /// @@ -277,27 +154,8 @@ public required string Source /// public required string Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentNullException("type") - ); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -305,29 +163,11 @@ public required string Type /// public required string UpdatedAt { - get - { - if (!this._rawData.TryGetValue("updated_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'updated_at' cannot be null", - new ArgumentOutOfRangeException("updated_at", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'updated_at' cannot be null", - new ArgumentNullException("updated_at") - ); - } - init - { - this._rawData["updated_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "updated_at"); } + init { ModelBase.Set(this._rawData, "updated_at", value); } } + /// public override void Validate() { _ = this.ID; @@ -341,6 +181,9 @@ public override void Validate() public Data() { } + public Data(Data data) + : base(data) { } + public Data(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -354,6 +197,7 @@ public Data(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static Data FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -362,6 +206,7 @@ public static Data FromRawUnchecked(IReadOnlyDictionary raw class DataFromRaw : IFromRaw { + /// public Data FromRawUnchecked(IReadOnlyDictionary rawData) => Data.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Beta/Skills/SkillListParams.cs b/src/Anthropic/Models/Beta/Skills/SkillListParams.cs index 0626a471..23932a5f 100644 --- a/src/Anthropic/Models/Beta/Skills/SkillListParams.cs +++ b/src/Anthropic/Models/Beta/Skills/SkillListParams.cs @@ -21,13 +21,7 @@ public sealed record class SkillListParams : ParamsBase /// public long? Limit { - get - { - if (!this._rawQueryData.TryGetValue("limit", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawQueryData, "limit"); } init { if (value == null) @@ -35,10 +29,7 @@ public long? Limit return; } - this._rawQueryData["limit"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "limit", value); } } @@ -50,20 +41,8 @@ public long? Limit /// public string? Page { - get - { - if (!this._rawQueryData.TryGetValue("page", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawQueryData["page"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawQueryData, "page"); } + init { ModelBase.Set(this._rawQueryData, "page", value); } } /// @@ -75,20 +54,8 @@ public string? Page /// public string? Source { - get - { - if (!this._rawQueryData.TryGetValue("source", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawQueryData["source"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawQueryData, "source"); } + init { ModelBase.Set(this._rawQueryData, "source", value); } } /// @@ -98,12 +65,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -113,15 +77,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public SkillListParams() { } + public SkillListParams(SkillListParams skillListParams) + : base(skillListParams) { } + public SkillListParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -143,6 +107,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static SkillListParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Skills/SkillRetrieveParams.cs b/src/Anthropic/Models/Beta/Skills/SkillRetrieveParams.cs index 47a1211d..545ad7be 100644 --- a/src/Anthropic/Models/Beta/Skills/SkillRetrieveParams.cs +++ b/src/Anthropic/Models/Beta/Skills/SkillRetrieveParams.cs @@ -23,12 +23,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -38,15 +35,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public SkillRetrieveParams() { } + public SkillRetrieveParams(SkillRetrieveParams skillRetrieveParams) + : base(skillRetrieveParams) { } + public SkillRetrieveParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -68,6 +65,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static SkillRetrieveParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Skills/SkillRetrieveResponse.cs b/src/Anthropic/Models/Beta/Skills/SkillRetrieveResponse.cs index d7bd3b42..51bc2ce2 100644 --- a/src/Anthropic/Models/Beta/Skills/SkillRetrieveResponse.cs +++ b/src/Anthropic/Models/Beta/Skills/SkillRetrieveResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Skills; @@ -19,27 +17,8 @@ public sealed record class SkillRetrieveResponse : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -47,27 +26,8 @@ public required string ID /// public required string CreatedAt { - get - { - if (!this._rawData.TryGetValue("created_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new ArgumentOutOfRangeException("created_at", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new ArgumentNullException("created_at") - ); - } - init - { - this._rawData["created_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "created_at"); } + init { ModelBase.Set(this._rawData, "created_at", value); } } /// @@ -78,20 +38,8 @@ public required string CreatedAt /// public required string? DisplayTitle { - get - { - if (!this._rawData.TryGetValue("display_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["display_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "display_title"); } + init { ModelBase.Set(this._rawData, "display_title", value); } } /// @@ -101,20 +49,8 @@ public required string? DisplayTitle /// public required string? LatestVersion { - get - { - if (!this._rawData.TryGetValue("latest_version", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["latest_version"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "latest_version"); } + init { ModelBase.Set(this._rawData, "latest_version", value); } } /// @@ -125,27 +61,8 @@ public required string? LatestVersion /// public required string Source { - get - { - if (!this._rawData.TryGetValue("source", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentOutOfRangeException("source", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentNullException("source") - ); - } - init - { - this._rawData["source"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "source"); } + init { ModelBase.Set(this._rawData, "source", value); } } /// @@ -155,27 +72,8 @@ public required string Source /// public required string Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentNullException("type") - ); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -183,29 +81,11 @@ public required string Type /// public required string UpdatedAt { - get - { - if (!this._rawData.TryGetValue("updated_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'updated_at' cannot be null", - new ArgumentOutOfRangeException("updated_at", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'updated_at' cannot be null", - new ArgumentNullException("updated_at") - ); - } - init - { - this._rawData["updated_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "updated_at"); } + init { ModelBase.Set(this._rawData, "updated_at", value); } } + /// public override void Validate() { _ = this.ID; @@ -219,6 +99,9 @@ public override void Validate() public SkillRetrieveResponse() { } + public SkillRetrieveResponse(SkillRetrieveResponse skillRetrieveResponse) + : base(skillRetrieveResponse) { } + public SkillRetrieveResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -232,6 +115,7 @@ public SkillRetrieveResponse(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static SkillRetrieveResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -242,6 +126,7 @@ IReadOnlyDictionary rawData class SkillRetrieveResponseFromRaw : IFromRaw { + /// public SkillRetrieveResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => SkillRetrieveResponse.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Skills/Versions/VersionCreateParams.cs b/src/Anthropic/Models/Beta/Skills/Versions/VersionCreateParams.cs index 56f5aef2..ea43c258 100644 --- a/src/Anthropic/Models/Beta/Skills/Versions/VersionCreateParams.cs +++ b/src/Anthropic/Models/Beta/Skills/Versions/VersionCreateParams.cs @@ -31,20 +31,8 @@ public IReadOnlyDictionary RawBodyData /// public IReadOnlyList? Files { - get - { - if (!this._rawBodyData.TryGetValue("files", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } - init - { - this._rawBodyData["files"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawBodyData, "files"); } + init { ModelBase.Set(this._rawBodyData, "files", value); } } /// @@ -54,12 +42,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -69,15 +54,18 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public VersionCreateParams() { } + public VersionCreateParams(VersionCreateParams versionCreateParams) + : base(versionCreateParams) + { + this._rawBodyData = [.. versionCreateParams._rawBodyData]; + } + public VersionCreateParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, @@ -103,6 +91,7 @@ FrozenDictionary rawBodyData } #pragma warning restore CS8618 + /// public static VersionCreateParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, diff --git a/src/Anthropic/Models/Beta/Skills/Versions/VersionCreateResponse.cs b/src/Anthropic/Models/Beta/Skills/Versions/VersionCreateResponse.cs index c08d99eb..246914f4 100644 --- a/src/Anthropic/Models/Beta/Skills/Versions/VersionCreateResponse.cs +++ b/src/Anthropic/Models/Beta/Skills/Versions/VersionCreateResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Skills.Versions; @@ -19,27 +17,8 @@ public sealed record class VersionCreateResponse : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -47,27 +26,8 @@ public required string ID /// public required string CreatedAt { - get - { - if (!this._rawData.TryGetValue("created_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new ArgumentOutOfRangeException("created_at", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new ArgumentNullException("created_at") - ); - } - init - { - this._rawData["created_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "created_at"); } + init { ModelBase.Set(this._rawData, "created_at", value); } } /// @@ -77,27 +37,8 @@ public required string CreatedAt /// public required string Description { - get - { - if (!this._rawData.TryGetValue("description", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'description' cannot be null", - new ArgumentOutOfRangeException("description", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'description' cannot be null", - new ArgumentNullException("description") - ); - } - init - { - this._rawData["description"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "description"); } + init { ModelBase.Set(this._rawData, "description", value); } } /// @@ -107,27 +48,8 @@ public required string Description /// public required string Directory { - get - { - if (!this._rawData.TryGetValue("directory", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'directory' cannot be null", - new ArgumentOutOfRangeException("directory", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'directory' cannot be null", - new ArgumentNullException("directory") - ); - } - init - { - this._rawData["directory"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "directory"); } + init { ModelBase.Set(this._rawData, "directory", value); } } /// @@ -137,27 +59,8 @@ public required string Directory /// public required string Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentNullException("name") - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } /// @@ -165,27 +68,8 @@ public required string Name /// public required string SkillID { - get - { - if (!this._rawData.TryGetValue("skill_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'skill_id' cannot be null", - new ArgumentOutOfRangeException("skill_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'skill_id' cannot be null", - new ArgumentNullException("skill_id") - ); - } - init - { - this._rawData["skill_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "skill_id"); } + init { ModelBase.Set(this._rawData, "skill_id", value); } } /// @@ -195,27 +79,8 @@ public required string SkillID /// public required string Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentNullException("type") - ); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -225,29 +90,11 @@ public required string Type /// public required string Version { - get - { - if (!this._rawData.TryGetValue("version", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'version' cannot be null", - new ArgumentOutOfRangeException("version", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'version' cannot be null", - new ArgumentNullException("version") - ); - } - init - { - this._rawData["version"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "version"); } + init { ModelBase.Set(this._rawData, "version", value); } } + /// public override void Validate() { _ = this.ID; @@ -262,6 +109,9 @@ public override void Validate() public VersionCreateResponse() { } + public VersionCreateResponse(VersionCreateResponse versionCreateResponse) + : base(versionCreateResponse) { } + public VersionCreateResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -275,6 +125,7 @@ public VersionCreateResponse(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static VersionCreateResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -285,6 +136,7 @@ IReadOnlyDictionary rawData class VersionCreateResponseFromRaw : IFromRaw { + /// public VersionCreateResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => VersionCreateResponse.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Skills/Versions/VersionDeleteParams.cs b/src/Anthropic/Models/Beta/Skills/Versions/VersionDeleteParams.cs index 19837e5c..52894ee7 100644 --- a/src/Anthropic/Models/Beta/Skills/Versions/VersionDeleteParams.cs +++ b/src/Anthropic/Models/Beta/Skills/Versions/VersionDeleteParams.cs @@ -25,12 +25,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -40,15 +37,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public VersionDeleteParams() { } + public VersionDeleteParams(VersionDeleteParams versionDeleteParams) + : base(versionDeleteParams) { } + public VersionDeleteParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -70,6 +67,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static VersionDeleteParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Skills/Versions/VersionDeleteResponse.cs b/src/Anthropic/Models/Beta/Skills/Versions/VersionDeleteResponse.cs index 405d62f5..6d4528c8 100644 --- a/src/Anthropic/Models/Beta/Skills/Versions/VersionDeleteResponse.cs +++ b/src/Anthropic/Models/Beta/Skills/Versions/VersionDeleteResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Skills.Versions; @@ -19,27 +17,8 @@ public sealed record class VersionDeleteResponse : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -49,29 +28,11 @@ public required string ID /// public required string Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentNullException("type") - ); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ID; @@ -80,6 +41,9 @@ public override void Validate() public VersionDeleteResponse() { } + public VersionDeleteResponse(VersionDeleteResponse versionDeleteResponse) + : base(versionDeleteResponse) { } + public VersionDeleteResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -93,6 +57,7 @@ public VersionDeleteResponse(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static VersionDeleteResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -103,6 +68,7 @@ IReadOnlyDictionary rawData class VersionDeleteResponseFromRaw : IFromRaw { + /// public VersionDeleteResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => VersionDeleteResponse.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Skills/Versions/VersionListPageResponse.cs b/src/Anthropic/Models/Beta/Skills/Versions/VersionListPageResponse.cs index b8a2c6b0..a8e28248 100644 --- a/src/Anthropic/Models/Beta/Skills/Versions/VersionListPageResponse.cs +++ b/src/Anthropic/Models/Beta/Skills/Versions/VersionListPageResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Skills.Versions; @@ -19,27 +17,11 @@ public sealed record class VersionListPageResponse : ModelBase { get { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize< - List - >(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNotNullClass< + List + >(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } /// @@ -47,23 +29,8 @@ public sealed record class VersionListPageResponse : ModelBase /// public required bool HasMore { - get - { - if (!this._rawData.TryGetValue("has_more", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'has_more' cannot be null", - new ArgumentOutOfRangeException("has_more", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["has_more"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "has_more"); } + init { ModelBase.Set(this._rawData, "has_more", value); } } /// @@ -72,22 +39,11 @@ public required bool HasMore /// public required string? NextPage { - get - { - if (!this._rawData.TryGetValue("next_page", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["next_page"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "next_page"); } + init { ModelBase.Set(this._rawData, "next_page", value); } } + /// public override void Validate() { foreach (var item in this.Data) @@ -100,6 +56,9 @@ public override void Validate() public VersionListPageResponse() { } + public VersionListPageResponse(VersionListPageResponse versionListPageResponse) + : base(versionListPageResponse) { } + public VersionListPageResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -113,6 +72,7 @@ public VersionListPageResponse(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static VersionListPageResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -123,6 +83,7 @@ IReadOnlyDictionary rawData class VersionListPageResponseFromRaw : IFromRaw { + /// public VersionListPageResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => VersionListPageResponse.FromRawUnchecked(rawData); @@ -143,27 +104,8 @@ public sealed record class Data : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -171,27 +113,8 @@ public required string ID /// public required string CreatedAt { - get - { - if (!this._rawData.TryGetValue("created_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new ArgumentOutOfRangeException("created_at", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new ArgumentNullException("created_at") - ); - } - init - { - this._rawData["created_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "created_at"); } + init { ModelBase.Set(this._rawData, "created_at", value); } } /// @@ -201,27 +124,8 @@ public required string CreatedAt /// public required string Description { - get - { - if (!this._rawData.TryGetValue("description", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'description' cannot be null", - new ArgumentOutOfRangeException("description", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'description' cannot be null", - new ArgumentNullException("description") - ); - } - init - { - this._rawData["description"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "description"); } + init { ModelBase.Set(this._rawData, "description", value); } } /// @@ -231,27 +135,8 @@ public required string Description /// public required string Directory { - get - { - if (!this._rawData.TryGetValue("directory", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'directory' cannot be null", - new ArgumentOutOfRangeException("directory", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'directory' cannot be null", - new ArgumentNullException("directory") - ); - } - init - { - this._rawData["directory"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "directory"); } + init { ModelBase.Set(this._rawData, "directory", value); } } /// @@ -261,27 +146,8 @@ public required string Directory /// public required string Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentNullException("name") - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } /// @@ -289,27 +155,8 @@ public required string Name /// public required string SkillID { - get - { - if (!this._rawData.TryGetValue("skill_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'skill_id' cannot be null", - new ArgumentOutOfRangeException("skill_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'skill_id' cannot be null", - new ArgumentNullException("skill_id") - ); - } - init - { - this._rawData["skill_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "skill_id"); } + init { ModelBase.Set(this._rawData, "skill_id", value); } } /// @@ -319,27 +166,8 @@ public required string SkillID /// public required string Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentNullException("type") - ); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -349,29 +177,11 @@ public required string Type /// public required string Version { - get - { - if (!this._rawData.TryGetValue("version", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'version' cannot be null", - new ArgumentOutOfRangeException("version", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'version' cannot be null", - new ArgumentNullException("version") - ); - } - init - { - this._rawData["version"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "version"); } + init { ModelBase.Set(this._rawData, "version", value); } } + /// public override void Validate() { _ = this.ID; @@ -386,6 +196,9 @@ public override void Validate() public Data() { } + public Data(global::Anthropic.Models.Beta.Skills.Versions.Data data) + : base(data) { } + public Data(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -399,6 +212,7 @@ public Data(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static global::Anthropic.Models.Beta.Skills.Versions.Data FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -409,6 +223,7 @@ IReadOnlyDictionary rawData class DataFromRaw : IFromRaw { + /// public global::Anthropic.Models.Beta.Skills.Versions.Data FromRawUnchecked( IReadOnlyDictionary rawData ) => global::Anthropic.Models.Beta.Skills.Versions.Data.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Beta/Skills/Versions/VersionListParams.cs b/src/Anthropic/Models/Beta/Skills/Versions/VersionListParams.cs index c18eb341..76a58d45 100644 --- a/src/Anthropic/Models/Beta/Skills/Versions/VersionListParams.cs +++ b/src/Anthropic/Models/Beta/Skills/Versions/VersionListParams.cs @@ -23,20 +23,8 @@ public sealed record class VersionListParams : ParamsBase /// public long? Limit { - get - { - if (!this._rawQueryData.TryGetValue("limit", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawQueryData["limit"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawQueryData, "limit"); } + init { ModelBase.Set(this._rawQueryData, "limit", value); } } /// @@ -44,20 +32,8 @@ public long? Limit /// public string? Page { - get - { - if (!this._rawQueryData.TryGetValue("page", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawQueryData["page"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawQueryData, "page"); } + init { ModelBase.Set(this._rawQueryData, "page", value); } } /// @@ -67,12 +43,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -82,15 +55,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public VersionListParams() { } + public VersionListParams(VersionListParams versionListParams) + : base(versionListParams) { } + public VersionListParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -112,6 +85,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static VersionListParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Skills/Versions/VersionRetrieveParams.cs b/src/Anthropic/Models/Beta/Skills/Versions/VersionRetrieveParams.cs index 342a12cb..1b9bb327 100644 --- a/src/Anthropic/Models/Beta/Skills/Versions/VersionRetrieveParams.cs +++ b/src/Anthropic/Models/Beta/Skills/Versions/VersionRetrieveParams.cs @@ -25,12 +25,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -40,15 +37,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public VersionRetrieveParams() { } + public VersionRetrieveParams(VersionRetrieveParams versionRetrieveParams) + : base(versionRetrieveParams) { } + public VersionRetrieveParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -70,6 +67,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static VersionRetrieveParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Beta/Skills/Versions/VersionRetrieveResponse.cs b/src/Anthropic/Models/Beta/Skills/Versions/VersionRetrieveResponse.cs index 1524a5f8..3eba38bc 100644 --- a/src/Anthropic/Models/Beta/Skills/Versions/VersionRetrieveResponse.cs +++ b/src/Anthropic/Models/Beta/Skills/Versions/VersionRetrieveResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Beta.Skills.Versions; @@ -19,27 +17,8 @@ public sealed record class VersionRetrieveResponse : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -47,27 +26,8 @@ public required string ID /// public required string CreatedAt { - get - { - if (!this._rawData.TryGetValue("created_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new ArgumentOutOfRangeException("created_at", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new ArgumentNullException("created_at") - ); - } - init - { - this._rawData["created_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "created_at"); } + init { ModelBase.Set(this._rawData, "created_at", value); } } /// @@ -77,27 +37,8 @@ public required string CreatedAt /// public required string Description { - get - { - if (!this._rawData.TryGetValue("description", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'description' cannot be null", - new ArgumentOutOfRangeException("description", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'description' cannot be null", - new ArgumentNullException("description") - ); - } - init - { - this._rawData["description"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "description"); } + init { ModelBase.Set(this._rawData, "description", value); } } /// @@ -107,27 +48,8 @@ public required string Description /// public required string Directory { - get - { - if (!this._rawData.TryGetValue("directory", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'directory' cannot be null", - new ArgumentOutOfRangeException("directory", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'directory' cannot be null", - new ArgumentNullException("directory") - ); - } - init - { - this._rawData["directory"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "directory"); } + init { ModelBase.Set(this._rawData, "directory", value); } } /// @@ -137,27 +59,8 @@ public required string Directory /// public required string Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentNullException("name") - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } /// @@ -165,27 +68,8 @@ public required string Name /// public required string SkillID { - get - { - if (!this._rawData.TryGetValue("skill_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'skill_id' cannot be null", - new ArgumentOutOfRangeException("skill_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'skill_id' cannot be null", - new ArgumentNullException("skill_id") - ); - } - init - { - this._rawData["skill_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "skill_id"); } + init { ModelBase.Set(this._rawData, "skill_id", value); } } /// @@ -195,27 +79,8 @@ public required string SkillID /// public required string Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentNullException("type") - ); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -225,29 +90,11 @@ public required string Type /// public required string Version { - get - { - if (!this._rawData.TryGetValue("version", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'version' cannot be null", - new ArgumentOutOfRangeException("version", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'version' cannot be null", - new ArgumentNullException("version") - ); - } - init - { - this._rawData["version"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "version"); } + init { ModelBase.Set(this._rawData, "version", value); } } + /// public override void Validate() { _ = this.ID; @@ -262,6 +109,9 @@ public override void Validate() public VersionRetrieveResponse() { } + public VersionRetrieveResponse(VersionRetrieveResponse versionRetrieveResponse) + : base(versionRetrieveResponse) { } + public VersionRetrieveResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -275,6 +125,7 @@ public VersionRetrieveResponse(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static VersionRetrieveResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -285,6 +136,7 @@ IReadOnlyDictionary rawData class VersionRetrieveResponseFromRaw : IFromRaw { + /// public VersionRetrieveResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => VersionRetrieveResponse.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/BillingError.cs b/src/Anthropic/Models/BillingError.cs index 48fc8a65..56e8d5c9 100644 --- a/src/Anthropic/Models/BillingError.cs +++ b/src/Anthropic/Models/BillingError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class BillingError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public BillingError() this.Type = JsonSerializer.Deserialize("\"billing_error\""); } + public BillingError(BillingError billingError) + : base(billingError) { } + public BillingError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public BillingError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BillingError FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -107,6 +77,7 @@ public BillingError(string message) class BillingErrorFromRaw : IFromRaw { + /// public BillingError FromRawUnchecked(IReadOnlyDictionary rawData) => BillingError.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/ErrorObject.cs b/src/Anthropic/Models/ErrorObject.cs index df996177..b7e4e63e 100644 --- a/src/Anthropic/Models/ErrorObject.cs +++ b/src/Anthropic/Models/ErrorObject.cs @@ -113,60 +113,222 @@ public ErrorObject(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickInvalidRequestError(out var value)) { + /// // `value` is of type `InvalidRequestError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickInvalidRequestError([NotNullWhen(true)] out InvalidRequestError? value) { value = this.Value as InvalidRequestError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickAuthenticationError(out var value)) { + /// // `value` is of type `AuthenticationError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickAuthenticationError([NotNullWhen(true)] out AuthenticationError? value) { value = this.Value as AuthenticationError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBillingError(out var value)) { + /// // `value` is of type `BillingError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBillingError([NotNullWhen(true)] out BillingError? value) { value = this.Value as BillingError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickPermissionError(out var value)) { + /// // `value` is of type `PermissionError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickPermissionError([NotNullWhen(true)] out PermissionError? value) { value = this.Value as PermissionError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickNotFoundError(out var value)) { + /// // `value` is of type `NotFoundError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickNotFoundError([NotNullWhen(true)] out NotFoundError? value) { value = this.Value as NotFoundError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickRateLimitError(out var value)) { + /// // `value` is of type `RateLimitError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickRateLimitError([NotNullWhen(true)] out RateLimitError? value) { value = this.Value as RateLimitError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickGatewayTimeoutError(out var value)) { + /// // `value` is of type `GatewayTimeoutError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickGatewayTimeoutError([NotNullWhen(true)] out GatewayTimeoutError? value) { value = this.Value as GatewayTimeoutError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickAPI(out var value)) { + /// // `value` is of type `APIErrorObject` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickAPI([NotNullWhen(true)] out APIErrorObject? value) { value = this.Value as APIErrorObject; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickOverloadedError(out var value)) { + /// // `value` is of type `OverloadedError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickOverloadedError([NotNullWhen(true)] out OverloadedError? value) { value = this.Value as OverloadedError; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (InvalidRequestError value) => {...}, + /// (AuthenticationError value) => {...}, + /// (BillingError value) => {...}, + /// (PermissionError value) => {...}, + /// (NotFoundError value) => {...}, + /// (RateLimitError value) => {...}, + /// (GatewayTimeoutError value) => {...}, + /// (APIErrorObject value) => {...}, + /// (OverloadedError value) => {...} + /// ); + /// + /// + /// public void Switch( Action invalidRequestError, Action authenticationError, @@ -215,6 +377,34 @@ Action overloadedError } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (InvalidRequestError value) => {...}, + /// (AuthenticationError value) => {...}, + /// (BillingError value) => {...}, + /// (PermissionError value) => {...}, + /// (NotFoundError value) => {...}, + /// (RateLimitError value) => {...}, + /// (GatewayTimeoutError value) => {...}, + /// (APIErrorObject value) => {...}, + /// (OverloadedError value) => {...} + /// ); + /// + /// + /// public T Match( Func invalidRequestError, Func authenticationError, @@ -262,6 +452,16 @@ Func overloadedError public static implicit operator ErrorObject(OverloadedError value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -270,6 +470,27 @@ public void Validate() "Data did not match any variant of ErrorObject" ); } + this.Switch( + (invalidRequestError) => invalidRequestError.Validate(), + (authenticationError) => authenticationError.Validate(), + (billingError) => billingError.Validate(), + (permissionError) => permissionError.Validate(), + (notFoundError) => notFoundError.Validate(), + (rateLimitError) => rateLimitError.Validate(), + (gatewayTimeoutError) => gatewayTimeoutError.Validate(), + (api) => api.Validate(), + (overloadedError) => overloadedError.Validate() + ); + } + + public virtual bool Equals(ErrorObject? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/ErrorResponse.cs b/src/Anthropic/Models/ErrorResponse.cs index c63f2364..131e8692 100644 --- a/src/Anthropic/Models/ErrorResponse.cs +++ b/src/Anthropic/Models/ErrorResponse.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,68 +13,23 @@ public sealed record class ErrorResponse : ModelBase { public required ErrorObject Error { - get - { - if (!this._rawData.TryGetValue("error", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error' cannot be null", - new ArgumentOutOfRangeException("error", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'error' cannot be null", - new ArgumentNullException("error") - ); - } - init - { - this._rawData["error"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "error"); } + init { ModelBase.Set(this._rawData, "error", value); } } public required string? RequestID { - get - { - if (!this._rawData.TryGetValue("request_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["request_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "request_id"); } + init { ModelBase.Set(this._rawData, "request_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Error.Validate(); @@ -93,6 +47,9 @@ public ErrorResponse() this.Type = JsonSerializer.Deserialize("\"error\""); } + public ErrorResponse(ErrorResponse errorResponse) + : base(errorResponse) { } + public ErrorResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -108,6 +65,7 @@ public ErrorResponse(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ErrorResponse FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -116,6 +74,7 @@ public static ErrorResponse FromRawUnchecked(IReadOnlyDictionary { + /// public ErrorResponse FromRawUnchecked(IReadOnlyDictionary rawData) => ErrorResponse.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/GatewayTimeoutError.cs b/src/Anthropic/Models/GatewayTimeoutError.cs index cda42437..2dc0336d 100644 --- a/src/Anthropic/Models/GatewayTimeoutError.cs +++ b/src/Anthropic/Models/GatewayTimeoutError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class GatewayTimeoutError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public GatewayTimeoutError() this.Type = JsonSerializer.Deserialize("\"timeout_error\""); } + public GatewayTimeoutError(GatewayTimeoutError gatewayTimeoutError) + : base(gatewayTimeoutError) { } + public GatewayTimeoutError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public GatewayTimeoutError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static GatewayTimeoutError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public GatewayTimeoutError(string message) class GatewayTimeoutErrorFromRaw : IFromRaw { + /// public GatewayTimeoutError FromRawUnchecked(IReadOnlyDictionary rawData) => GatewayTimeoutError.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/InvalidRequestError.cs b/src/Anthropic/Models/InvalidRequestError.cs index 3b9166f3..a030d340 100644 --- a/src/Anthropic/Models/InvalidRequestError.cs +++ b/src/Anthropic/Models/InvalidRequestError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class InvalidRequestError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public InvalidRequestError() this.Type = JsonSerializer.Deserialize("\"invalid_request_error\""); } + public InvalidRequestError(InvalidRequestError invalidRequestError) + : base(invalidRequestError) { } + public InvalidRequestError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public InvalidRequestError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static InvalidRequestError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public InvalidRequestError(string message) class InvalidRequestErrorFromRaw : IFromRaw { + /// public InvalidRequestError FromRawUnchecked(IReadOnlyDictionary rawData) => InvalidRequestError.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/Base64ImageSource.cs b/src/Anthropic/Models/Messages/Base64ImageSource.cs index fab09a8b..97377cc8 100644 --- a/src/Anthropic/Models/Messages/Base64ImageSource.cs +++ b/src/Anthropic/Models/Messages/Base64ImageSource.cs @@ -14,77 +14,29 @@ public sealed record class Base64ImageSource : ModelBase { public required string Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new System::ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new System::ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } public required ApiEnum MediaType { get { - if (!this._rawData.TryGetValue("media_type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'media_type' cannot be null", - new System::ArgumentOutOfRangeException( - "media_type", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["media_type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "media_type" ); } + init { ModelBase.Set(this._rawData, "media_type", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Data; @@ -105,6 +57,9 @@ public Base64ImageSource() this.Type = JsonSerializer.Deserialize("\"base64\""); } + public Base64ImageSource(Base64ImageSource base64ImageSource) + : base(base64ImageSource) { } + public Base64ImageSource(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -120,6 +75,7 @@ public Base64ImageSource(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static Base64ImageSource FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -130,6 +86,7 @@ IReadOnlyDictionary rawData class Base64ImageSourceFromRaw : IFromRaw { + /// public Base64ImageSource FromRawUnchecked(IReadOnlyDictionary rawData) => Base64ImageSource.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/Base64PDFSource.cs b/src/Anthropic/Models/Messages/Base64PDFSource.cs index a899ec7c..b6d8e9f2 100644 --- a/src/Anthropic/Models/Messages/Base64PDFSource.cs +++ b/src/Anthropic/Models/Messages/Base64PDFSource.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,71 +13,23 @@ public sealed record class Base64PDFSource : ModelBase { public required string Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } public JsonElement MediaType { - get - { - if (!this._rawData.TryGetValue("media_type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'media_type' cannot be null", - new ArgumentOutOfRangeException("media_type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["media_type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "media_type"); } + init { ModelBase.Set(this._rawData, "media_type", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Data; @@ -108,6 +59,9 @@ public Base64PDFSource() this.Type = JsonSerializer.Deserialize("\"base64\""); } + public Base64PDFSource(Base64PDFSource base64PDFSource) + : base(base64PDFSource) { } + public Base64PDFSource(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -124,6 +78,7 @@ public Base64PDFSource(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static Base64PDFSource FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -139,6 +94,7 @@ public Base64PDFSource(string data) class Base64PDFSourceFromRaw : IFromRaw { + /// public Base64PDFSource FromRawUnchecked(IReadOnlyDictionary rawData) => Base64PDFSource.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/Batches/BatchCancelParams.cs b/src/Anthropic/Models/Messages/Batches/BatchCancelParams.cs index df073b73..606bdf8e 100644 --- a/src/Anthropic/Models/Messages/Batches/BatchCancelParams.cs +++ b/src/Anthropic/Models/Messages/Batches/BatchCancelParams.cs @@ -25,6 +25,9 @@ public sealed record class BatchCancelParams : ParamsBase public BatchCancelParams() { } + public BatchCancelParams(BatchCancelParams batchCancelParams) + : base(batchCancelParams) { } + public BatchCancelParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -46,6 +49,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static BatchCancelParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Messages/Batches/BatchCreateParams.cs b/src/Anthropic/Models/Messages/Batches/BatchCreateParams.cs index b3f9a647..611dbf08 100644 --- a/src/Anthropic/Models/Messages/Batches/BatchCreateParams.cs +++ b/src/Anthropic/Models/Messages/Batches/BatchCreateParams.cs @@ -35,31 +35,18 @@ public IReadOnlyDictionary RawBodyData /// public required IReadOnlyList Requests { - get - { - if (!this._rawBodyData.TryGetValue("requests", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'requests' cannot be null", - new System::ArgumentOutOfRangeException("requests", "Missing required argument") - ); - - return JsonSerializer.Deserialize>(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'requests' cannot be null", - new System::ArgumentNullException("requests") - ); - } - init - { - this._rawBodyData["requests"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawBodyData, "requests"); } + init { ModelBase.Set(this._rawBodyData, "requests", value); } } public BatchCreateParams() { } + public BatchCreateParams(BatchCreateParams batchCreateParams) + : base(batchCreateParams) + { + this._rawBodyData = [.. batchCreateParams._rawBodyData]; + } + public BatchCreateParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, @@ -85,6 +72,7 @@ FrozenDictionary rawBodyData } #pragma warning restore CS8618 + /// public static BatchCreateParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, @@ -134,30 +122,8 @@ public sealed record class Request : ModelBase /// public required string CustomID { - get - { - if (!this._rawData.TryGetValue("custom_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'custom_id' cannot be null", - new System::ArgumentOutOfRangeException( - "custom_id", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'custom_id' cannot be null", - new System::ArgumentNullException("custom_id") - ); - } - init - { - this._rawData["custom_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "custom_id"); } + init { ModelBase.Set(this._rawData, "custom_id", value); } } /// @@ -168,29 +134,11 @@ public required string CustomID /// public required Params Params { - get - { - if (!this._rawData.TryGetValue("params", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'params' cannot be null", - new System::ArgumentOutOfRangeException("params", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'params' cannot be null", - new System::ArgumentNullException("params") - ); - } - init - { - this._rawData["params"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "params"); } + init { ModelBase.Set(this._rawData, "params", value); } } + /// public override void Validate() { _ = this.CustomID; @@ -199,6 +147,9 @@ public override void Validate() public Request() { } + public Request(Request request) + : base(request) { } + public Request(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -212,6 +163,7 @@ public Request(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static Request FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -220,6 +172,7 @@ public static Request FromRawUnchecked(IReadOnlyDictionary class RequestFromRaw : IFromRaw { + /// public Request FromRawUnchecked(IReadOnlyDictionary rawData) => Request.FromRawUnchecked(rawData); } @@ -244,26 +197,8 @@ public sealed record class Params : ModelBase /// public required long MaxTokens { - get - { - if (!this._rawData.TryGetValue("max_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'max_tokens' cannot be null", - new System::ArgumentOutOfRangeException( - "max_tokens", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["max_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "max_tokens"); } + init { ModelBase.Set(this._rawData, "max_tokens", value); } } /// @@ -319,30 +254,8 @@ public required long MaxTokens /// public required IReadOnlyList Messages { - get - { - if (!this._rawData.TryGetValue("messages", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'messages' cannot be null", - new System::ArgumentOutOfRangeException("messages", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'messages' cannot be null", - new System::ArgumentNullException("messages") - ); - } - init - { - this._rawData["messages"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "messages"); } + init { ModelBase.Set(this._rawData, "messages", value); } } /// @@ -351,26 +264,8 @@ public required IReadOnlyList Messages /// public required ApiEnum Model { - get - { - if (!this._rawData.TryGetValue("model", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'model' cannot be null", - new System::ArgumentOutOfRangeException("model", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["model"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "model"); } + init { ModelBase.Set(this._rawData, "model", value); } } /// @@ -378,13 +273,7 @@ public required ApiEnum Model /// public Metadata? Metadata { - get - { - if (!this._rawData.TryGetValue("metadata", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawData, "metadata"); } init { if (value == null) @@ -392,10 +281,7 @@ public Metadata? Metadata return; } - this._rawData["metadata"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "metadata", value); } } @@ -410,13 +296,9 @@ public Metadata? Metadata { get { - if (!this._rawData.TryGetValue("service_tier", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); + return ModelBase.GetNullableClass< + ApiEnum + >(this.RawData, "service_tier"); } init { @@ -425,10 +307,7 @@ public Metadata? Metadata return; } - this._rawData["service_tier"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "service_tier", value); } } @@ -446,13 +325,7 @@ public Metadata? Metadata /// public IReadOnlyList? StopSequences { - get - { - if (!this._rawData.TryGetValue("stop_sequences", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass>(this.RawData, "stop_sequences"); } init { if (value == null) @@ -460,10 +333,7 @@ public IReadOnlyList? StopSequences return; } - this._rawData["stop_sequences"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "stop_sequences", value); } } @@ -475,13 +345,7 @@ public IReadOnlyList? StopSequences /// public bool? Stream { - get - { - if (!this._rawData.TryGetValue("stream", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "stream"); } init { if (value == null) @@ -489,10 +353,7 @@ public bool? Stream return; } - this._rawData["stream"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "stream", value); } } @@ -504,13 +365,7 @@ public bool? Stream /// public ParamsSystem? System { - get - { - if (!this._rawData.TryGetValue("system", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawData, "system"); } init { if (value == null) @@ -518,10 +373,7 @@ public ParamsSystem? System return; } - this._rawData["system"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "system", value); } } @@ -537,13 +389,7 @@ public ParamsSystem? System /// public double? Temperature { - get - { - if (!this._rawData.TryGetValue("temperature", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "temperature"); } init { if (value == null) @@ -551,10 +397,7 @@ public double? Temperature return; } - this._rawData["temperature"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "temperature", value); } } @@ -570,16 +413,7 @@ public double? Temperature /// public ThinkingConfigParam? Thinking { - get - { - if (!this._rawData.TryGetValue("thinking", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "thinking"); } init { if (value == null) @@ -587,10 +421,7 @@ public ThinkingConfigParam? Thinking return; } - this._rawData["thinking"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "thinking", value); } } @@ -600,13 +431,7 @@ public ThinkingConfigParam? Thinking /// public ToolChoice? ToolChoice { - get - { - if (!this._rawData.TryGetValue("tool_choice", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawData, "tool_choice"); } init { if (value == null) @@ -614,10 +439,7 @@ public ToolChoice? ToolChoice return; } - this._rawData["tool_choice"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "tool_choice", value); } } @@ -670,16 +492,7 @@ public ToolChoice? ToolChoice /// public IReadOnlyList? Tools { - get - { - if (!this._rawData.TryGetValue("tools", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "tools"); } init { if (value == null) @@ -687,10 +500,7 @@ public IReadOnlyList? Tools return; } - this._rawData["tools"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "tools", value); } } @@ -704,13 +514,7 @@ public IReadOnlyList? Tools /// public long? TopK { - get - { - if (!this._rawData.TryGetValue("top_k", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "top_k"); } init { if (value == null) @@ -718,10 +522,7 @@ public long? TopK return; } - this._rawData["top_k"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "top_k", value); } } @@ -737,13 +538,7 @@ public long? TopK /// public double? TopP { - get - { - if (!this._rawData.TryGetValue("top_p", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "top_p"); } init { if (value == null) @@ -751,13 +546,11 @@ public double? TopP return; } - this._rawData["top_p"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "top_p", value); } } + /// public override void Validate() { _ = this.MaxTokens; @@ -784,6 +577,9 @@ public override void Validate() public Params() { } + public Params(Params params1) + : base(params1) { } + public Params(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -797,6 +593,7 @@ public Params(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static Params FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -805,6 +602,7 @@ public static Params FromRawUnchecked(IReadOnlyDictionary r class ParamsFromRaw : IFromRaw { + /// public Params FromRawUnchecked(IReadOnlyDictionary rawData) => Params.FromRawUnchecked(rawData); } @@ -897,18 +695,68 @@ public ParamsSystem(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTextBlockParams(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTextBlockParams([NotNullWhen(true)] out IReadOnlyList? value) { value = this.Value as IReadOnlyList; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action @string, System::Action> textBlockParams @@ -929,6 +777,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match( System::Func @string, System::Func, T> textBlockParams @@ -949,6 +818,16 @@ public T Match( public static implicit operator ParamsSystem(List value) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -958,6 +837,16 @@ public void Validate() ); } } + + public virtual bool Equals(ParamsSystem? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } } sealed class ParamsSystemConverter : JsonConverter diff --git a/src/Anthropic/Models/Messages/Batches/BatchDeleteParams.cs b/src/Anthropic/Models/Messages/Batches/BatchDeleteParams.cs index ddafb1da..99c22daf 100644 --- a/src/Anthropic/Models/Messages/Batches/BatchDeleteParams.cs +++ b/src/Anthropic/Models/Messages/Batches/BatchDeleteParams.cs @@ -22,6 +22,9 @@ public sealed record class BatchDeleteParams : ParamsBase public BatchDeleteParams() { } + public BatchDeleteParams(BatchDeleteParams batchDeleteParams) + : base(batchDeleteParams) { } + public BatchDeleteParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -43,6 +46,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static BatchDeleteParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Messages/Batches/BatchListPageResponse.cs b/src/Anthropic/Models/Messages/Batches/BatchListPageResponse.cs index c428d013..c5d84356 100644 --- a/src/Anthropic/Models/Messages/Batches/BatchListPageResponse.cs +++ b/src/Anthropic/Models/Messages/Batches/BatchListPageResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Messages.Batches; @@ -14,30 +12,8 @@ public sealed record class BatchListPageResponse : ModelBase { public required IReadOnlyList Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } /// @@ -45,20 +21,8 @@ public required IReadOnlyList Data /// public required string? FirstID { - get - { - if (!this._rawData.TryGetValue("first_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["first_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "first_id"); } + init { ModelBase.Set(this._rawData, "first_id", value); } } /// @@ -66,23 +30,8 @@ public required string? FirstID /// public required bool HasMore { - get - { - if (!this._rawData.TryGetValue("has_more", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'has_more' cannot be null", - new ArgumentOutOfRangeException("has_more", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["has_more"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "has_more"); } + init { ModelBase.Set(this._rawData, "has_more", value); } } /// @@ -90,22 +39,11 @@ public required bool HasMore /// public required string? LastID { - get - { - if (!this._rawData.TryGetValue("last_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["last_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "last_id"); } + init { ModelBase.Set(this._rawData, "last_id", value); } } + /// public override void Validate() { foreach (var item in this.Data) @@ -119,6 +57,9 @@ public override void Validate() public BatchListPageResponse() { } + public BatchListPageResponse(BatchListPageResponse batchListPageResponse) + : base(batchListPageResponse) { } + public BatchListPageResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -132,6 +73,7 @@ public BatchListPageResponse(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static BatchListPageResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -142,6 +84,7 @@ IReadOnlyDictionary rawData class BatchListPageResponseFromRaw : IFromRaw { + /// public BatchListPageResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => BatchListPageResponse.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/Batches/BatchListParams.cs b/src/Anthropic/Models/Messages/Batches/BatchListParams.cs index 705d3bd6..87260e37 100644 --- a/src/Anthropic/Models/Messages/Batches/BatchListParams.cs +++ b/src/Anthropic/Models/Messages/Batches/BatchListParams.cs @@ -22,13 +22,7 @@ public sealed record class BatchListParams : ParamsBase /// public string? AfterID { - get - { - if (!this._rawQueryData.TryGetValue("after_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawQueryData, "after_id"); } init { if (value == null) @@ -36,10 +30,7 @@ public string? AfterID return; } - this._rawQueryData["after_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "after_id", value); } } @@ -49,13 +40,7 @@ public string? AfterID /// public string? BeforeID { - get - { - if (!this._rawQueryData.TryGetValue("before_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawQueryData, "before_id"); } init { if (value == null) @@ -63,10 +48,7 @@ public string? BeforeID return; } - this._rawQueryData["before_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "before_id", value); } } @@ -77,13 +59,7 @@ public string? BeforeID /// public long? Limit { - get - { - if (!this._rawQueryData.TryGetValue("limit", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawQueryData, "limit"); } init { if (value == null) @@ -91,15 +67,15 @@ public long? Limit return; } - this._rawQueryData["limit"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "limit", value); } } public BatchListParams() { } + public BatchListParams(BatchListParams batchListParams) + : base(batchListParams) { } + public BatchListParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -121,6 +97,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static BatchListParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Messages/Batches/BatchResultsParams.cs b/src/Anthropic/Models/Messages/Batches/BatchResultsParams.cs index 90c73097..7936c54c 100644 --- a/src/Anthropic/Models/Messages/Batches/BatchResultsParams.cs +++ b/src/Anthropic/Models/Messages/Batches/BatchResultsParams.cs @@ -23,6 +23,9 @@ public sealed record class BatchResultsParams : ParamsBase public BatchResultsParams() { } + public BatchResultsParams(BatchResultsParams batchResultsParams) + : base(batchResultsParams) { } + public BatchResultsParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -44,6 +47,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static BatchResultsParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Messages/Batches/BatchRetrieveParams.cs b/src/Anthropic/Models/Messages/Batches/BatchRetrieveParams.cs index 1418b537..7f199c86 100644 --- a/src/Anthropic/Models/Messages/Batches/BatchRetrieveParams.cs +++ b/src/Anthropic/Models/Messages/Batches/BatchRetrieveParams.cs @@ -21,6 +21,9 @@ public sealed record class BatchRetrieveParams : ParamsBase public BatchRetrieveParams() { } + public BatchRetrieveParams(BatchRetrieveParams batchRetrieveParams) + : base(batchRetrieveParams) { } + public BatchRetrieveParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -42,6 +45,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static BatchRetrieveParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Messages/Batches/DeletedMessageBatch.cs b/src/Anthropic/Models/Messages/Batches/DeletedMessageBatch.cs index 8e655c55..bf78f14f 100644 --- a/src/Anthropic/Models/Messages/Batches/DeletedMessageBatch.cs +++ b/src/Anthropic/Models/Messages/Batches/DeletedMessageBatch.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -17,27 +16,8 @@ public sealed record class DeletedMessageBatch : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -47,25 +27,11 @@ public required string ID /// public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ID; @@ -85,6 +51,9 @@ public DeletedMessageBatch() this.Type = JsonSerializer.Deserialize("\"message_batch_deleted\""); } + public DeletedMessageBatch(DeletedMessageBatch deletedMessageBatch) + : base(deletedMessageBatch) { } + public DeletedMessageBatch(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -100,6 +69,7 @@ public DeletedMessageBatch(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static DeletedMessageBatch FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -117,6 +87,7 @@ public DeletedMessageBatch(string id) class DeletedMessageBatchFromRaw : IFromRaw { + /// public DeletedMessageBatch FromRawUnchecked(IReadOnlyDictionary rawData) => DeletedMessageBatch.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/Batches/MessageBatch.cs b/src/Anthropic/Models/Messages/Batches/MessageBatch.cs index d98efbe8..1856dc79 100644 --- a/src/Anthropic/Models/Messages/Batches/MessageBatch.cs +++ b/src/Anthropic/Models/Messages/Batches/MessageBatch.cs @@ -19,27 +19,8 @@ public sealed record class MessageBatch : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new System::ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new System::ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -50,21 +31,9 @@ public required string ID { get { - if (!this._rawData.TryGetValue("archived_at", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["archived_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableStruct(this.RawData, "archived_at"); } + init { ModelBase.Set(this._rawData, "archived_at", value); } } /// @@ -75,21 +44,12 @@ public required string ID { get { - if (!this._rawData.TryGetValue("cancel_initiated_at", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cancel_initiated_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableStruct( + this.RawData, + "cancel_initiated_at" ); } + init { ModelBase.Set(this._rawData, "cancel_initiated_at", value); } } /// @@ -100,27 +60,9 @@ public required string ID { get { - if (!this._rawData.TryGetValue("created_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new System::ArgumentOutOfRangeException( - "created_at", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["created_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNotNullStruct(this.RawData, "created_at"); } + init { ModelBase.Set(this._rawData, "created_at", value); } } /// @@ -134,21 +76,9 @@ public required string ID { get { - if (!this._rawData.TryGetValue("ended_at", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["ended_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableStruct(this.RawData, "ended_at"); } + init { ModelBase.Set(this._rawData, "ended_at", value); } } /// @@ -159,27 +89,9 @@ public required string ID { get { - if (!this._rawData.TryGetValue("expires_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'expires_at' cannot be null", - new System::ArgumentOutOfRangeException( - "expires_at", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["expires_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNotNullStruct(this.RawData, "expires_at"); } + init { ModelBase.Set(this._rawData, "expires_at", value); } } /// @@ -189,27 +101,12 @@ public required ApiEnum ProcessingStatus { get { - if (!this._rawData.TryGetValue("processing_status", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'processing_status' cannot be null", - new System::ArgumentOutOfRangeException( - "processing_status", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["processing_status"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "processing_status" ); } + init { ModelBase.Set(this._rawData, "processing_status", value); } } /// @@ -223,31 +120,12 @@ public required MessageBatchRequestCounts RequestCounts { get { - if (!this._rawData.TryGetValue("request_counts", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'request_counts' cannot be null", - new System::ArgumentOutOfRangeException( - "request_counts", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'request_counts' cannot be null", - new System::ArgumentNullException("request_counts") - ); - } - init - { - this._rawData["request_counts"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "request_counts" ); } + init { ModelBase.Set(this._rawData, "request_counts", value); } } /// @@ -259,20 +137,8 @@ public required MessageBatchRequestCounts RequestCounts /// public required string? ResultsURL { - get - { - if (!this._rawData.TryGetValue("results_url", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["results_url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "results_url"); } + init { ModelBase.Set(this._rawData, "results_url", value); } } /// @@ -282,25 +148,11 @@ public required string? ResultsURL /// public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ID; @@ -328,6 +180,9 @@ public MessageBatch() this.Type = JsonSerializer.Deserialize("\"message_batch\""); } + public MessageBatch(MessageBatch messageBatch) + : base(messageBatch) { } + public MessageBatch(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -343,6 +198,7 @@ public MessageBatch(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static MessageBatch FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -351,6 +207,7 @@ public static MessageBatch FromRawUnchecked(IReadOnlyDictionary { + /// public MessageBatch FromRawUnchecked(IReadOnlyDictionary rawData) => MessageBatch.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/Batches/MessageBatchCanceledResult.cs b/src/Anthropic/Models/Messages/Batches/MessageBatchCanceledResult.cs index 87d6c775..70dfb4d6 100644 --- a/src/Anthropic/Models/Messages/Batches/MessageBatchCanceledResult.cs +++ b/src/Anthropic/Models/Messages/Batches/MessageBatchCanceledResult.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,25 +15,11 @@ public sealed record class MessageBatchCanceledResult : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { if ( @@ -53,6 +38,9 @@ public MessageBatchCanceledResult() this.Type = JsonSerializer.Deserialize("\"canceled\""); } + public MessageBatchCanceledResult(MessageBatchCanceledResult messageBatchCanceledResult) + : base(messageBatchCanceledResult) { } + public MessageBatchCanceledResult(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -68,6 +56,7 @@ public MessageBatchCanceledResult(IReadOnlyDictionary rawDa } #pragma warning restore CS8618 + /// public static MessageBatchCanceledResult FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -78,6 +67,7 @@ IReadOnlyDictionary rawData class MessageBatchCanceledResultFromRaw : IFromRaw { + /// public MessageBatchCanceledResult FromRawUnchecked( IReadOnlyDictionary rawData ) => MessageBatchCanceledResult.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/Batches/MessageBatchErroredResult.cs b/src/Anthropic/Models/Messages/Batches/MessageBatchErroredResult.cs index f47729cc..c1c11010 100644 --- a/src/Anthropic/Models/Messages/Batches/MessageBatchErroredResult.cs +++ b/src/Anthropic/Models/Messages/Batches/MessageBatchErroredResult.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class MessageBatchErroredResult : ModelBase { public required ErrorResponse Error { - get - { - if (!this._rawData.TryGetValue("error", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error' cannot be null", - new ArgumentOutOfRangeException("error", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'error' cannot be null", - new ArgumentNullException("error") - ); - } - init - { - this._rawData["error"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "error"); } + init { ModelBase.Set(this._rawData, "error", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Error.Validate(); @@ -77,6 +43,9 @@ public MessageBatchErroredResult() this.Type = JsonSerializer.Deserialize("\"errored\""); } + public MessageBatchErroredResult(MessageBatchErroredResult messageBatchErroredResult) + : base(messageBatchErroredResult) { } + public MessageBatchErroredResult(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public MessageBatchErroredResult(IReadOnlyDictionary rawDat } #pragma warning restore CS8618 + /// public static MessageBatchErroredResult FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public MessageBatchErroredResult(ErrorResponse error) class MessageBatchErroredResultFromRaw : IFromRaw { + /// public MessageBatchErroredResult FromRawUnchecked( IReadOnlyDictionary rawData ) => MessageBatchErroredResult.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/Batches/MessageBatchExpiredResult.cs b/src/Anthropic/Models/Messages/Batches/MessageBatchExpiredResult.cs index 0998d999..518a8442 100644 --- a/src/Anthropic/Models/Messages/Batches/MessageBatchExpiredResult.cs +++ b/src/Anthropic/Models/Messages/Batches/MessageBatchExpiredResult.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,25 +13,11 @@ public sealed record class MessageBatchExpiredResult : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { if ( @@ -51,6 +36,9 @@ public MessageBatchExpiredResult() this.Type = JsonSerializer.Deserialize("\"expired\""); } + public MessageBatchExpiredResult(MessageBatchExpiredResult messageBatchExpiredResult) + : base(messageBatchExpiredResult) { } + public MessageBatchExpiredResult(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -66,6 +54,7 @@ public MessageBatchExpiredResult(IReadOnlyDictionary rawDat } #pragma warning restore CS8618 + /// public static MessageBatchExpiredResult FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -76,6 +65,7 @@ IReadOnlyDictionary rawData class MessageBatchExpiredResultFromRaw : IFromRaw { + /// public MessageBatchExpiredResult FromRawUnchecked( IReadOnlyDictionary rawData ) => MessageBatchExpiredResult.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/Batches/MessageBatchIndividualResponse.cs b/src/Anthropic/Models/Messages/Batches/MessageBatchIndividualResponse.cs index 3d4b24fd..3c761d9b 100644 --- a/src/Anthropic/Models/Messages/Batches/MessageBatchIndividualResponse.cs +++ b/src/Anthropic/Models/Messages/Batches/MessageBatchIndividualResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Messages.Batches; @@ -26,27 +24,8 @@ public sealed record class MessageBatchIndividualResponse : ModelBase /// public required string CustomID { - get - { - if (!this._rawData.TryGetValue("custom_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'custom_id' cannot be null", - new ArgumentOutOfRangeException("custom_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'custom_id' cannot be null", - new ArgumentNullException("custom_id") - ); - } - init - { - this._rawData["custom_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "custom_id"); } + init { ModelBase.Set(this._rawData, "custom_id", value); } } /// @@ -58,32 +37,11 @@ public required string CustomID /// public required MessageBatchResult Result { - get - { - if (!this._rawData.TryGetValue("result", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'result' cannot be null", - new ArgumentOutOfRangeException("result", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'result' cannot be null", - new ArgumentNullException("result") - ); - } - init - { - this._rawData["result"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "result"); } + init { ModelBase.Set(this._rawData, "result", value); } } + /// public override void Validate() { _ = this.CustomID; @@ -92,6 +50,11 @@ public override void Validate() public MessageBatchIndividualResponse() { } + public MessageBatchIndividualResponse( + MessageBatchIndividualResponse messageBatchIndividualResponse + ) + : base(messageBatchIndividualResponse) { } + public MessageBatchIndividualResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -105,6 +68,7 @@ public MessageBatchIndividualResponse(IReadOnlyDictionary r } #pragma warning restore CS8618 + /// public static MessageBatchIndividualResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -115,6 +79,7 @@ IReadOnlyDictionary rawData class MessageBatchIndividualResponseFromRaw : IFromRaw { + /// public MessageBatchIndividualResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => MessageBatchIndividualResponse.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/Batches/MessageBatchRequestCounts.cs b/src/Anthropic/Models/Messages/Batches/MessageBatchRequestCounts.cs index a3f562ad..ff4b3cdb 100644 --- a/src/Anthropic/Models/Messages/Batches/MessageBatchRequestCounts.cs +++ b/src/Anthropic/Models/Messages/Batches/MessageBatchRequestCounts.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Messages.Batches; @@ -19,23 +17,8 @@ public sealed record class MessageBatchRequestCounts : ModelBase /// public required long Canceled { - get - { - if (!this._rawData.TryGetValue("canceled", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'canceled' cannot be null", - new ArgumentOutOfRangeException("canceled", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["canceled"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "canceled"); } + init { ModelBase.Set(this._rawData, "canceled", value); } } /// @@ -45,23 +28,8 @@ public required long Canceled /// public required long Errored { - get - { - if (!this._rawData.TryGetValue("errored", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'errored' cannot be null", - new ArgumentOutOfRangeException("errored", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["errored"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "errored"); } + init { ModelBase.Set(this._rawData, "errored", value); } } /// @@ -71,23 +39,8 @@ public required long Errored /// public required long Expired { - get - { - if (!this._rawData.TryGetValue("expired", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'expired' cannot be null", - new ArgumentOutOfRangeException("expired", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["expired"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "expired"); } + init { ModelBase.Set(this._rawData, "expired", value); } } /// @@ -95,23 +48,8 @@ public required long Expired /// public required long Processing { - get - { - if (!this._rawData.TryGetValue("processing", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'processing' cannot be null", - new ArgumentOutOfRangeException("processing", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["processing"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "processing"); } + init { ModelBase.Set(this._rawData, "processing", value); } } /// @@ -121,25 +59,11 @@ public required long Processing /// public required long Succeeded { - get - { - if (!this._rawData.TryGetValue("succeeded", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'succeeded' cannot be null", - new ArgumentOutOfRangeException("succeeded", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["succeeded"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "succeeded"); } + init { ModelBase.Set(this._rawData, "succeeded", value); } } + /// public override void Validate() { _ = this.Canceled; @@ -151,6 +75,9 @@ public override void Validate() public MessageBatchRequestCounts() { } + public MessageBatchRequestCounts(MessageBatchRequestCounts messageBatchRequestCounts) + : base(messageBatchRequestCounts) { } + public MessageBatchRequestCounts(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -164,6 +91,7 @@ public MessageBatchRequestCounts(IReadOnlyDictionary rawDat } #pragma warning restore CS8618 + /// public static MessageBatchRequestCounts FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -174,6 +102,7 @@ IReadOnlyDictionary rawData class MessageBatchRequestCountsFromRaw : IFromRaw { + /// public MessageBatchRequestCounts FromRawUnchecked( IReadOnlyDictionary rawData ) => MessageBatchRequestCounts.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/Batches/MessageBatchResult.cs b/src/Anthropic/Models/Messages/Batches/MessageBatchResult.cs index 5d8218fd..26bbeb19 100644 --- a/src/Anthropic/Models/Messages/Batches/MessageBatchResult.cs +++ b/src/Anthropic/Models/Messages/Batches/MessageBatchResult.cs @@ -67,30 +67,112 @@ public MessageBatchResult(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickSucceeded(out var value)) { + /// // `value` is of type `MessageBatchSucceededResult` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickSucceeded([NotNullWhen(true)] out MessageBatchSucceededResult? value) { value = this.Value as MessageBatchSucceededResult; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickErrored(out var value)) { + /// // `value` is of type `MessageBatchErroredResult` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickErrored([NotNullWhen(true)] out MessageBatchErroredResult? value) { value = this.Value as MessageBatchErroredResult; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCanceled(out var value)) { + /// // `value` is of type `MessageBatchCanceledResult` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCanceled([NotNullWhen(true)] out MessageBatchCanceledResult? value) { value = this.Value as MessageBatchCanceledResult; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickExpired(out var value)) { + /// // `value` is of type `MessageBatchExpiredResult` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickExpired([NotNullWhen(true)] out MessageBatchExpiredResult? value) { value = this.Value as MessageBatchExpiredResult; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (MessageBatchSucceededResult value) => {...}, + /// (MessageBatchErroredResult value) => {...}, + /// (MessageBatchCanceledResult value) => {...}, + /// (MessageBatchExpiredResult value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action succeeded, System::Action errored, @@ -119,6 +201,29 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (MessageBatchSucceededResult value) => {...}, + /// (MessageBatchErroredResult value) => {...}, + /// (MessageBatchCanceledResult value) => {...}, + /// (MessageBatchExpiredResult value) => {...} + /// ); + /// + /// + /// public T Match( System::Func succeeded, System::Func errored, @@ -150,6 +255,16 @@ public static implicit operator MessageBatchResult(MessageBatchCanceledResult va public static implicit operator MessageBatchResult(MessageBatchExpiredResult value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -158,6 +273,22 @@ public void Validate() "Data did not match any variant of MessageBatchResult" ); } + this.Switch( + (succeeded) => succeeded.Validate(), + (errored) => errored.Validate(), + (canceled) => canceled.Validate(), + (expired) => expired.Validate() + ); + } + + public virtual bool Equals(MessageBatchResult? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/Batches/MessageBatchSucceededResult.cs b/src/Anthropic/Models/Messages/Batches/MessageBatchSucceededResult.cs index 510f4802..66889a41 100644 --- a/src/Anthropic/Models/Messages/Batches/MessageBatchSucceededResult.cs +++ b/src/Anthropic/Models/Messages/Batches/MessageBatchSucceededResult.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,50 +15,17 @@ public sealed record class MessageBatchSucceededResult : ModelBase { public required Message Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Message.Validate(); @@ -79,6 +45,9 @@ public MessageBatchSucceededResult() this.Type = JsonSerializer.Deserialize("\"succeeded\""); } + public MessageBatchSucceededResult(MessageBatchSucceededResult messageBatchSucceededResult) + : base(messageBatchSucceededResult) { } + public MessageBatchSucceededResult(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -94,6 +63,7 @@ public MessageBatchSucceededResult(IReadOnlyDictionary rawD } #pragma warning restore CS8618 + /// public static MessageBatchSucceededResult FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -111,6 +81,7 @@ public MessageBatchSucceededResult(Message message) class MessageBatchSucceededResultFromRaw : IFromRaw { + /// public MessageBatchSucceededResult FromRawUnchecked( IReadOnlyDictionary rawData ) => MessageBatchSucceededResult.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/CacheControlEphemeral.cs b/src/Anthropic/Models/Messages/CacheControlEphemeral.cs index 4340a270..1d40341f 100644 --- a/src/Anthropic/Models/Messages/CacheControlEphemeral.cs +++ b/src/Anthropic/Models/Messages/CacheControlEphemeral.cs @@ -14,23 +14,8 @@ public sealed record class CacheControlEphemeral : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -42,16 +27,7 @@ public JsonElement Type /// public ApiEnum? TTL { - get - { - if (!this._rawData.TryGetValue("ttl", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "ttl"); } init { if (value == null) @@ -59,13 +35,11 @@ public ApiEnum? TTL return; } - this._rawData["ttl"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "ttl", value); } } + /// public override void Validate() { if ( @@ -85,6 +59,9 @@ public CacheControlEphemeral() this.Type = JsonSerializer.Deserialize("\"ephemeral\""); } + public CacheControlEphemeral(CacheControlEphemeral cacheControlEphemeral) + : base(cacheControlEphemeral) { } + public CacheControlEphemeral(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -100,6 +77,7 @@ public CacheControlEphemeral(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static CacheControlEphemeral FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -110,6 +88,7 @@ IReadOnlyDictionary rawData class CacheControlEphemeralFromRaw : IFromRaw { + /// public CacheControlEphemeral FromRawUnchecked( IReadOnlyDictionary rawData ) => CacheControlEphemeral.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/CacheCreation.cs b/src/Anthropic/Models/Messages/CacheCreation.cs index dc2ca498..c34dd1c0 100644 --- a/src/Anthropic/Models/Messages/CacheCreation.cs +++ b/src/Anthropic/Models/Messages/CacheCreation.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Messages; @@ -17,26 +15,8 @@ public sealed record class CacheCreation : ModelBase /// public required long Ephemeral1hInputTokens { - get - { - if (!this._rawData.TryGetValue("ephemeral_1h_input_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'ephemeral_1h_input_tokens' cannot be null", - new ArgumentOutOfRangeException( - "ephemeral_1h_input_tokens", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["ephemeral_1h_input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "ephemeral_1h_input_tokens"); } + init { ModelBase.Set(this._rawData, "ephemeral_1h_input_tokens", value); } } /// @@ -44,28 +24,11 @@ public required long Ephemeral1hInputTokens /// public required long Ephemeral5mInputTokens { - get - { - if (!this._rawData.TryGetValue("ephemeral_5m_input_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'ephemeral_5m_input_tokens' cannot be null", - new ArgumentOutOfRangeException( - "ephemeral_5m_input_tokens", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["ephemeral_5m_input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "ephemeral_5m_input_tokens"); } + init { ModelBase.Set(this._rawData, "ephemeral_5m_input_tokens", value); } } + /// public override void Validate() { _ = this.Ephemeral1hInputTokens; @@ -74,6 +37,9 @@ public override void Validate() public CacheCreation() { } + public CacheCreation(CacheCreation cacheCreation) + : base(cacheCreation) { } + public CacheCreation(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -87,6 +53,7 @@ public CacheCreation(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static CacheCreation FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -95,6 +62,7 @@ public static CacheCreation FromRawUnchecked(IReadOnlyDictionary { + /// public CacheCreation FromRawUnchecked(IReadOnlyDictionary rawData) => CacheCreation.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/CitationCharLocation.cs b/src/Anthropic/Models/Messages/CitationCharLocation.cs index cabf7d23..35cf7ff7 100644 --- a/src/Anthropic/Models/Messages/CitationCharLocation.cs +++ b/src/Anthropic/Models/Messages/CitationCharLocation.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,149 +13,47 @@ public sealed record class CitationCharLocation : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long DocumentIndex { - get - { - if (!this._rawData.TryGetValue("document_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'document_index' cannot be null", - new ArgumentOutOfRangeException("document_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "document_index"); } + init { ModelBase.Set(this._rawData, "document_index", value); } } public required string? DocumentTitle { - get - { - if (!this._rawData.TryGetValue("document_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "document_title"); } + init { ModelBase.Set(this._rawData, "document_title", value); } } public required long EndCharIndex { - get - { - if (!this._rawData.TryGetValue("end_char_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_char_index' cannot be null", - new ArgumentOutOfRangeException("end_char_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_char_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_char_index"); } + init { ModelBase.Set(this._rawData, "end_char_index", value); } } public required string? FileID { - get - { - if (!this._rawData.TryGetValue("file_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["file_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "file_id"); } + init { ModelBase.Set(this._rawData, "file_id", value); } } public required long StartCharIndex { - get - { - if (!this._rawData.TryGetValue("start_char_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_char_index' cannot be null", - new ArgumentOutOfRangeException("start_char_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_char_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_char_index"); } + init { ModelBase.Set(this._rawData, "start_char_index", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -181,6 +78,9 @@ public CitationCharLocation() this.Type = JsonSerializer.Deserialize("\"char_location\""); } + public CitationCharLocation(CitationCharLocation citationCharLocation) + : base(citationCharLocation) { } + public CitationCharLocation(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -196,6 +96,7 @@ public CitationCharLocation(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static CitationCharLocation FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -206,6 +107,7 @@ IReadOnlyDictionary rawData class CitationCharLocationFromRaw : IFromRaw { + /// public CitationCharLocation FromRawUnchecked( IReadOnlyDictionary rawData ) => CitationCharLocation.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/CitationCharLocationParam.cs b/src/Anthropic/Models/Messages/CitationCharLocationParam.cs index e6b10824..cc6b9453 100644 --- a/src/Anthropic/Models/Messages/CitationCharLocationParam.cs +++ b/src/Anthropic/Models/Messages/CitationCharLocationParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,131 +13,41 @@ public sealed record class CitationCharLocationParam : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long DocumentIndex { - get - { - if (!this._rawData.TryGetValue("document_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'document_index' cannot be null", - new ArgumentOutOfRangeException("document_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "document_index"); } + init { ModelBase.Set(this._rawData, "document_index", value); } } public required string? DocumentTitle { - get - { - if (!this._rawData.TryGetValue("document_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "document_title"); } + init { ModelBase.Set(this._rawData, "document_title", value); } } public required long EndCharIndex { - get - { - if (!this._rawData.TryGetValue("end_char_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_char_index' cannot be null", - new ArgumentOutOfRangeException("end_char_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_char_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_char_index"); } + init { ModelBase.Set(this._rawData, "end_char_index", value); } } public required long StartCharIndex { - get - { - if (!this._rawData.TryGetValue("start_char_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_char_index' cannot be null", - new ArgumentOutOfRangeException("start_char_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_char_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_char_index"); } + init { ModelBase.Set(this._rawData, "start_char_index", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -162,6 +71,9 @@ public CitationCharLocationParam() this.Type = JsonSerializer.Deserialize("\"char_location\""); } + public CitationCharLocationParam(CitationCharLocationParam citationCharLocationParam) + : base(citationCharLocationParam) { } + public CitationCharLocationParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -177,6 +89,7 @@ public CitationCharLocationParam(IReadOnlyDictionary rawDat } #pragma warning restore CS8618 + /// public static CitationCharLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -187,6 +100,7 @@ IReadOnlyDictionary rawData class CitationCharLocationParamFromRaw : IFromRaw { + /// public CitationCharLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) => CitationCharLocationParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/CitationContentBlockLocation.cs b/src/Anthropic/Models/Messages/CitationContentBlockLocation.cs index 20cc14ea..19bab4af 100644 --- a/src/Anthropic/Models/Messages/CitationContentBlockLocation.cs +++ b/src/Anthropic/Models/Messages/CitationContentBlockLocation.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,152 +15,47 @@ public sealed record class CitationContentBlockLocation : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long DocumentIndex { - get - { - if (!this._rawData.TryGetValue("document_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'document_index' cannot be null", - new ArgumentOutOfRangeException("document_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "document_index"); } + init { ModelBase.Set(this._rawData, "document_index", value); } } public required string? DocumentTitle { - get - { - if (!this._rawData.TryGetValue("document_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "document_title"); } + init { ModelBase.Set(this._rawData, "document_title", value); } } public required long EndBlockIndex { - get - { - if (!this._rawData.TryGetValue("end_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_block_index' cannot be null", - new ArgumentOutOfRangeException("end_block_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_block_index"); } + init { ModelBase.Set(this._rawData, "end_block_index", value); } } public required string? FileID { - get - { - if (!this._rawData.TryGetValue("file_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["file_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "file_id"); } + init { ModelBase.Set(this._rawData, "file_id", value); } } public required long StartBlockIndex { - get - { - if (!this._rawData.TryGetValue("start_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_block_index' cannot be null", - new ArgumentOutOfRangeException( - "start_block_index", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_block_index"); } + init { ModelBase.Set(this._rawData, "start_block_index", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -186,6 +80,9 @@ public CitationContentBlockLocation() this.Type = JsonSerializer.Deserialize("\"content_block_location\""); } + public CitationContentBlockLocation(CitationContentBlockLocation citationContentBlockLocation) + : base(citationContentBlockLocation) { } + public CitationContentBlockLocation(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -201,6 +98,7 @@ public CitationContentBlockLocation(IReadOnlyDictionary raw } #pragma warning restore CS8618 + /// public static CitationContentBlockLocation FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -211,6 +109,7 @@ IReadOnlyDictionary rawData class CitationContentBlockLocationFromRaw : IFromRaw { + /// public CitationContentBlockLocation FromRawUnchecked( IReadOnlyDictionary rawData ) => CitationContentBlockLocation.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/CitationContentBlockLocationParam.cs b/src/Anthropic/Models/Messages/CitationContentBlockLocationParam.cs index 992ecfed..792a8244 100644 --- a/src/Anthropic/Models/Messages/CitationContentBlockLocationParam.cs +++ b/src/Anthropic/Models/Messages/CitationContentBlockLocationParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,134 +18,41 @@ public sealed record class CitationContentBlockLocationParam : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long DocumentIndex { - get - { - if (!this._rawData.TryGetValue("document_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'document_index' cannot be null", - new ArgumentOutOfRangeException("document_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "document_index"); } + init { ModelBase.Set(this._rawData, "document_index", value); } } public required string? DocumentTitle { - get - { - if (!this._rawData.TryGetValue("document_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "document_title"); } + init { ModelBase.Set(this._rawData, "document_title", value); } } public required long EndBlockIndex { - get - { - if (!this._rawData.TryGetValue("end_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_block_index' cannot be null", - new ArgumentOutOfRangeException("end_block_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_block_index"); } + init { ModelBase.Set(this._rawData, "end_block_index", value); } } public required long StartBlockIndex { - get - { - if (!this._rawData.TryGetValue("start_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_block_index' cannot be null", - new ArgumentOutOfRangeException( - "start_block_index", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_block_index"); } + init { ModelBase.Set(this._rawData, "start_block_index", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -170,6 +76,11 @@ public CitationContentBlockLocationParam() this.Type = JsonSerializer.Deserialize("\"content_block_location\""); } + public CitationContentBlockLocationParam( + CitationContentBlockLocationParam citationContentBlockLocationParam + ) + : base(citationContentBlockLocationParam) { } + public CitationContentBlockLocationParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -185,6 +96,7 @@ public CitationContentBlockLocationParam(IReadOnlyDictionary public static CitationContentBlockLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -195,6 +107,7 @@ IReadOnlyDictionary rawData class CitationContentBlockLocationParamFromRaw : IFromRaw { + /// public CitationContentBlockLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) => CitationContentBlockLocationParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/CitationPageLocation.cs b/src/Anthropic/Models/Messages/CitationPageLocation.cs index 9e331302..51c21684 100644 --- a/src/Anthropic/Models/Messages/CitationPageLocation.cs +++ b/src/Anthropic/Models/Messages/CitationPageLocation.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,152 +13,47 @@ public sealed record class CitationPageLocation : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long DocumentIndex { - get - { - if (!this._rawData.TryGetValue("document_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'document_index' cannot be null", - new ArgumentOutOfRangeException("document_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "document_index"); } + init { ModelBase.Set(this._rawData, "document_index", value); } } public required string? DocumentTitle { - get - { - if (!this._rawData.TryGetValue("document_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "document_title"); } + init { ModelBase.Set(this._rawData, "document_title", value); } } public required long EndPageNumber { - get - { - if (!this._rawData.TryGetValue("end_page_number", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_page_number' cannot be null", - new ArgumentOutOfRangeException("end_page_number", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_page_number"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_page_number"); } + init { ModelBase.Set(this._rawData, "end_page_number", value); } } public required string? FileID { - get - { - if (!this._rawData.TryGetValue("file_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["file_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "file_id"); } + init { ModelBase.Set(this._rawData, "file_id", value); } } public required long StartPageNumber { - get - { - if (!this._rawData.TryGetValue("start_page_number", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_page_number' cannot be null", - new ArgumentOutOfRangeException( - "start_page_number", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_page_number"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_page_number"); } + init { ModelBase.Set(this._rawData, "start_page_number", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -184,6 +78,9 @@ public CitationPageLocation() this.Type = JsonSerializer.Deserialize("\"page_location\""); } + public CitationPageLocation(CitationPageLocation citationPageLocation) + : base(citationPageLocation) { } + public CitationPageLocation(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -199,6 +96,7 @@ public CitationPageLocation(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static CitationPageLocation FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -209,6 +107,7 @@ IReadOnlyDictionary rawData class CitationPageLocationFromRaw : IFromRaw { + /// public CitationPageLocation FromRawUnchecked( IReadOnlyDictionary rawData ) => CitationPageLocation.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/CitationPageLocationParam.cs b/src/Anthropic/Models/Messages/CitationPageLocationParam.cs index f9e00e8c..0a978b42 100644 --- a/src/Anthropic/Models/Messages/CitationPageLocationParam.cs +++ b/src/Anthropic/Models/Messages/CitationPageLocationParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,134 +13,41 @@ public sealed record class CitationPageLocationParam : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long DocumentIndex { - get - { - if (!this._rawData.TryGetValue("document_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'document_index' cannot be null", - new ArgumentOutOfRangeException("document_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "document_index"); } + init { ModelBase.Set(this._rawData, "document_index", value); } } public required string? DocumentTitle { - get - { - if (!this._rawData.TryGetValue("document_title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["document_title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "document_title"); } + init { ModelBase.Set(this._rawData, "document_title", value); } } public required long EndPageNumber { - get - { - if (!this._rawData.TryGetValue("end_page_number", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_page_number' cannot be null", - new ArgumentOutOfRangeException("end_page_number", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_page_number"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_page_number"); } + init { ModelBase.Set(this._rawData, "end_page_number", value); } } public required long StartPageNumber { - get - { - if (!this._rawData.TryGetValue("start_page_number", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_page_number' cannot be null", - new ArgumentOutOfRangeException( - "start_page_number", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_page_number"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_page_number"); } + init { ModelBase.Set(this._rawData, "start_page_number", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -165,6 +71,9 @@ public CitationPageLocationParam() this.Type = JsonSerializer.Deserialize("\"page_location\""); } + public CitationPageLocationParam(CitationPageLocationParam citationPageLocationParam) + : base(citationPageLocationParam) { } + public CitationPageLocationParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -180,6 +89,7 @@ public CitationPageLocationParam(IReadOnlyDictionary rawDat } #pragma warning restore CS8618 + /// public static CitationPageLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -190,6 +100,7 @@ IReadOnlyDictionary rawData class CitationPageLocationParamFromRaw : IFromRaw { + /// public CitationPageLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) => CitationPageLocationParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/CitationSearchResultLocationParam.cs b/src/Anthropic/Models/Messages/CitationSearchResultLocationParam.cs index b6cd9f33..f4fd3495 100644 --- a/src/Anthropic/Models/Messages/CitationSearchResultLocationParam.cs +++ b/src/Anthropic/Models/Messages/CitationSearchResultLocationParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,162 +18,47 @@ public sealed record class CitationSearchResultLocationParam : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long EndBlockIndex { - get - { - if (!this._rawData.TryGetValue("end_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_block_index' cannot be null", - new ArgumentOutOfRangeException("end_block_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_block_index"); } + init { ModelBase.Set(this._rawData, "end_block_index", value); } } public required long SearchResultIndex { - get - { - if (!this._rawData.TryGetValue("search_result_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'search_result_index' cannot be null", - new ArgumentOutOfRangeException( - "search_result_index", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["search_result_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "search_result_index"); } + init { ModelBase.Set(this._rawData, "search_result_index", value); } } public required string Source { - get - { - if (!this._rawData.TryGetValue("source", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentOutOfRangeException("source", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentNullException("source") - ); - } - init - { - this._rawData["source"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "source"); } + init { ModelBase.Set(this._rawData, "source", value); } } public required long StartBlockIndex { - get - { - if (!this._rawData.TryGetValue("start_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_block_index' cannot be null", - new ArgumentOutOfRangeException( - "start_block_index", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_block_index"); } + init { ModelBase.Set(this._rawData, "start_block_index", value); } } public required string? Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -199,6 +83,11 @@ public CitationSearchResultLocationParam() this.Type = JsonSerializer.Deserialize("\"search_result_location\""); } + public CitationSearchResultLocationParam( + CitationSearchResultLocationParam citationSearchResultLocationParam + ) + : base(citationSearchResultLocationParam) { } + public CitationSearchResultLocationParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -214,6 +103,7 @@ public CitationSearchResultLocationParam(IReadOnlyDictionary public static CitationSearchResultLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -224,6 +114,7 @@ IReadOnlyDictionary rawData class CitationSearchResultLocationParamFromRaw : IFromRaw { + /// public CitationSearchResultLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) => CitationSearchResultLocationParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/CitationWebSearchResultLocationParam.cs b/src/Anthropic/Models/Messages/CitationWebSearchResultLocationParam.cs index fe80870b..59543ccd 100644 --- a/src/Anthropic/Models/Messages/CitationWebSearchResultLocationParam.cs +++ b/src/Anthropic/Models/Messages/CitationWebSearchResultLocationParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,118 +18,35 @@ public sealed record class CitationWebSearchResultLocationParam : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required string EncryptedIndex { - get - { - if (!this._rawData.TryGetValue("encrypted_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'encrypted_index' cannot be null", - new ArgumentOutOfRangeException("encrypted_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'encrypted_index' cannot be null", - new ArgumentNullException("encrypted_index") - ); - } - init - { - this._rawData["encrypted_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "encrypted_index"); } + init { ModelBase.Set(this._rawData, "encrypted_index", value); } } public required string? Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required string URL { - get - { - if (!this._rawData.TryGetValue("url", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentOutOfRangeException("url", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentNullException("url") - ); - } - init - { - this._rawData["url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "url"); } + init { ModelBase.Set(this._rawData, "url", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -153,6 +69,11 @@ public CitationWebSearchResultLocationParam() this.Type = JsonSerializer.Deserialize("\"web_search_result_location\""); } + public CitationWebSearchResultLocationParam( + CitationWebSearchResultLocationParam citationWebSearchResultLocationParam + ) + : base(citationWebSearchResultLocationParam) { } + public CitationWebSearchResultLocationParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -168,6 +89,7 @@ public CitationWebSearchResultLocationParam(IReadOnlyDictionary public static CitationWebSearchResultLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -178,6 +100,7 @@ IReadOnlyDictionary rawData class CitationWebSearchResultLocationParamFromRaw : IFromRaw { + /// public CitationWebSearchResultLocationParam FromRawUnchecked( IReadOnlyDictionary rawData ) => CitationWebSearchResultLocationParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/CitationsConfigParam.cs b/src/Anthropic/Models/Messages/CitationsConfigParam.cs index 68a59136..34ceffcf 100644 --- a/src/Anthropic/Models/Messages/CitationsConfigParam.cs +++ b/src/Anthropic/Models/Messages/CitationsConfigParam.cs @@ -12,13 +12,7 @@ public sealed record class CitationsConfigParam : ModelBase { public bool? Enabled { - get - { - if (!this._rawData.TryGetValue("enabled", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "enabled"); } init { if (value == null) @@ -26,13 +20,11 @@ public bool? Enabled return; } - this._rawData["enabled"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "enabled", value); } } + /// public override void Validate() { _ = this.Enabled; @@ -40,6 +32,9 @@ public override void Validate() public CitationsConfigParam() { } + public CitationsConfigParam(CitationsConfigParam citationsConfigParam) + : base(citationsConfigParam) { } + public CitationsConfigParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -53,6 +48,7 @@ public CitationsConfigParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static CitationsConfigParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -63,6 +59,7 @@ IReadOnlyDictionary rawData class CitationsConfigParamFromRaw : IFromRaw { + /// public CitationsConfigParam FromRawUnchecked( IReadOnlyDictionary rawData ) => CitationsConfigParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/CitationsDelta.cs b/src/Anthropic/Models/Messages/CitationsDelta.cs index 3534bfdd..25531bdc 100644 --- a/src/Anthropic/Models/Messages/CitationsDelta.cs +++ b/src/Anthropic/Models/Messages/CitationsDelta.cs @@ -14,50 +14,17 @@ public sealed record class CitationsDelta : ModelBase { public required Citation Citation { - get - { - if (!this._rawData.TryGetValue("citation", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'citation' cannot be null", - new System::ArgumentOutOfRangeException("citation", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'citation' cannot be null", - new System::ArgumentNullException("citation") - ); - } - init - { - this._rawData["citation"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "citation"); } + init { ModelBase.Set(this._rawData, "citation", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Citation.Validate(); @@ -77,6 +44,9 @@ public CitationsDelta() this.Type = JsonSerializer.Deserialize("\"citations_delta\""); } + public CitationsDelta(CitationsDelta citationsDelta) + : base(citationsDelta) { } + public CitationsDelta(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +62,7 @@ public CitationsDelta(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static CitationsDelta FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -107,6 +78,7 @@ public CitationsDelta(Citation citation) class CitationsDeltaFromRaw : IFromRaw { + /// public CitationsDelta FromRawUnchecked(IReadOnlyDictionary rawData) => CitationsDelta.FromRawUnchecked(rawData); } @@ -270,18 +242,63 @@ public Citation(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCharLocation(out var value)) { + /// // `value` is of type `CitationCharLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCharLocation([NotNullWhen(true)] out CitationCharLocation? value) { value = this.Value as CitationCharLocation; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickPageLocation(out var value)) { + /// // `value` is of type `CitationPageLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickPageLocation([NotNullWhen(true)] out CitationPageLocation? value) { value = this.Value as CitationPageLocation; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickContentBlockLocation(out var value)) { + /// // `value` is of type `CitationContentBlockLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickContentBlockLocation( [NotNullWhen(true)] out CitationContentBlockLocation? value ) @@ -290,6 +307,21 @@ public bool TryPickContentBlockLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationsWebSearchResultLocation(out var value)) { + /// // `value` is of type `CitationsWebSearchResultLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationsWebSearchResultLocation( [NotNullWhen(true)] out CitationsWebSearchResultLocation? value ) @@ -298,6 +330,21 @@ public bool TryPickCitationsWebSearchResultLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationsSearchResultLocation(out var value)) { + /// // `value` is of type `CitationsSearchResultLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationsSearchResultLocation( [NotNullWhen(true)] out CitationsSearchResultLocation? value ) @@ -306,6 +353,29 @@ public bool TryPickCitationsSearchResultLocation( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (CitationCharLocation value) => {...}, + /// (CitationPageLocation value) => {...}, + /// (CitationContentBlockLocation value) => {...}, + /// (CitationsWebSearchResultLocation value) => {...}, + /// (CitationsSearchResultLocation value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action charLocation, System::Action pageLocation, @@ -338,6 +408,30 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (CitationCharLocation value) => {...}, + /// (CitationPageLocation value) => {...}, + /// (CitationContentBlockLocation value) => {...}, + /// (CitationsWebSearchResultLocation value) => {...}, + /// (CitationsSearchResultLocation value) => {...} + /// ); + /// + /// + /// public T Match( System::Func charLocation, System::Func pageLocation, @@ -369,12 +463,39 @@ public T Match( public static implicit operator Citation(CitationsSearchResultLocation value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of Citation"); } + this.Switch( + (charLocation) => charLocation.Validate(), + (pageLocation) => pageLocation.Validate(), + (contentBlockLocation) => contentBlockLocation.Validate(), + (citationsWebSearchResultLocation) => citationsWebSearchResultLocation.Validate(), + (citationsSearchResultLocation) => citationsSearchResultLocation.Validate() + ); + } + + public virtual bool Equals(Citation? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/CitationsSearchResultLocation.cs b/src/Anthropic/Models/Messages/CitationsSearchResultLocation.cs index ce224274..a3adcdac 100644 --- a/src/Anthropic/Models/Messages/CitationsSearchResultLocation.cs +++ b/src/Anthropic/Models/Messages/CitationsSearchResultLocation.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,162 +15,47 @@ public sealed record class CitationsSearchResultLocation : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required long EndBlockIndex { - get - { - if (!this._rawData.TryGetValue("end_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'end_block_index' cannot be null", - new ArgumentOutOfRangeException("end_block_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["end_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "end_block_index"); } + init { ModelBase.Set(this._rawData, "end_block_index", value); } } public required long SearchResultIndex { - get - { - if (!this._rawData.TryGetValue("search_result_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'search_result_index' cannot be null", - new ArgumentOutOfRangeException( - "search_result_index", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["search_result_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "search_result_index"); } + init { ModelBase.Set(this._rawData, "search_result_index", value); } } public required string Source { - get - { - if (!this._rawData.TryGetValue("source", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentOutOfRangeException("source", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentNullException("source") - ); - } - init - { - this._rawData["source"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "source"); } + init { ModelBase.Set(this._rawData, "source", value); } } public required long StartBlockIndex { - get - { - if (!this._rawData.TryGetValue("start_block_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'start_block_index' cannot be null", - new ArgumentOutOfRangeException( - "start_block_index", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["start_block_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "start_block_index"); } + init { ModelBase.Set(this._rawData, "start_block_index", value); } } public required string? Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -196,6 +80,11 @@ public CitationsSearchResultLocation() this.Type = JsonSerializer.Deserialize("\"search_result_location\""); } + public CitationsSearchResultLocation( + CitationsSearchResultLocation citationsSearchResultLocation + ) + : base(citationsSearchResultLocation) { } + public CitationsSearchResultLocation(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -211,6 +100,7 @@ public CitationsSearchResultLocation(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static CitationsSearchResultLocation FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -221,6 +111,7 @@ IReadOnlyDictionary rawData class CitationsSearchResultLocationFromRaw : IFromRaw { + /// public CitationsSearchResultLocation FromRawUnchecked( IReadOnlyDictionary rawData ) => CitationsSearchResultLocation.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/CitationsWebSearchResultLocation.cs b/src/Anthropic/Models/Messages/CitationsWebSearchResultLocation.cs index 2e37f435..a1f27e0a 100644 --- a/src/Anthropic/Models/Messages/CitationsWebSearchResultLocation.cs +++ b/src/Anthropic/Models/Messages/CitationsWebSearchResultLocation.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,118 +18,35 @@ public sealed record class CitationsWebSearchResultLocation : ModelBase { public required string CitedText { - get - { - if (!this._rawData.TryGetValue("cited_text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentOutOfRangeException("cited_text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'cited_text' cannot be null", - new ArgumentNullException("cited_text") - ); - } - init - { - this._rawData["cited_text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "cited_text"); } + init { ModelBase.Set(this._rawData, "cited_text", value); } } public required string EncryptedIndex { - get - { - if (!this._rawData.TryGetValue("encrypted_index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'encrypted_index' cannot be null", - new ArgumentOutOfRangeException("encrypted_index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'encrypted_index' cannot be null", - new ArgumentNullException("encrypted_index") - ); - } - init - { - this._rawData["encrypted_index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "encrypted_index"); } + init { ModelBase.Set(this._rawData, "encrypted_index", value); } } public required string? Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required string URL { - get - { - if (!this._rawData.TryGetValue("url", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentOutOfRangeException("url", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentNullException("url") - ); - } - init - { - this._rawData["url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "url"); } + init { ModelBase.Set(this._rawData, "url", value); } } + /// public override void Validate() { _ = this.CitedText; @@ -153,6 +69,11 @@ public CitationsWebSearchResultLocation() this.Type = JsonSerializer.Deserialize("\"web_search_result_location\""); } + public CitationsWebSearchResultLocation( + CitationsWebSearchResultLocation citationsWebSearchResultLocation + ) + : base(citationsWebSearchResultLocation) { } + public CitationsWebSearchResultLocation(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -168,6 +89,7 @@ public CitationsWebSearchResultLocation(IReadOnlyDictionary } #pragma warning restore CS8618 + /// public static CitationsWebSearchResultLocation FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -178,6 +100,7 @@ IReadOnlyDictionary rawData class CitationsWebSearchResultLocationFromRaw : IFromRaw { + /// public CitationsWebSearchResultLocation FromRawUnchecked( IReadOnlyDictionary rawData ) => CitationsWebSearchResultLocation.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/ContentBlock.cs b/src/Anthropic/Models/Messages/ContentBlock.cs index c9e07ef9..f6d66b80 100644 --- a/src/Anthropic/Models/Messages/ContentBlock.cs +++ b/src/Anthropic/Models/Messages/ContentBlock.cs @@ -89,42 +89,156 @@ public ContentBlock(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickText(out var value)) { + /// // `value` is of type `TextBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickText([NotNullWhen(true)] out TextBlock? value) { value = this.Value as TextBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickThinking(out var value)) { + /// // `value` is of type `ThinkingBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickThinking([NotNullWhen(true)] out ThinkingBlock? value) { value = this.Value as ThinkingBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickRedactedThinking(out var value)) { + /// // `value` is of type `RedactedThinkingBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickRedactedThinking([NotNullWhen(true)] out RedactedThinkingBlock? value) { value = this.Value as RedactedThinkingBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickToolUse(out var value)) { + /// // `value` is of type `ToolUseBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickToolUse([NotNullWhen(true)] out ToolUseBlock? value) { value = this.Value as ToolUseBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickServerToolUse(out var value)) { + /// // `value` is of type `ServerToolUseBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickServerToolUse([NotNullWhen(true)] out ServerToolUseBlock? value) { value = this.Value as ServerToolUseBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickWebSearchToolResult(out var value)) { + /// // `value` is of type `WebSearchToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickWebSearchToolResult([NotNullWhen(true)] out WebSearchToolResultBlock? value) { value = this.Value as WebSearchToolResultBlock; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (TextBlock value) => {...}, + /// (ThinkingBlock value) => {...}, + /// (RedactedThinkingBlock value) => {...}, + /// (ToolUseBlock value) => {...}, + /// (ServerToolUseBlock value) => {...}, + /// (WebSearchToolResultBlock value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action text, System::Action thinking, @@ -161,6 +275,31 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (TextBlock value) => {...}, + /// (ThinkingBlock value) => {...}, + /// (RedactedThinkingBlock value) => {...}, + /// (ToolUseBlock value) => {...}, + /// (ServerToolUseBlock value) => {...}, + /// (WebSearchToolResultBlock value) => {...} + /// ); + /// + /// + /// public T Match( System::Func text, System::Func thinking, @@ -196,6 +335,16 @@ public T Match( public static implicit operator ContentBlock(WebSearchToolResultBlock value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -204,6 +353,24 @@ public void Validate() "Data did not match any variant of ContentBlock" ); } + this.Switch( + (text) => text.Validate(), + (thinking) => thinking.Validate(), + (redactedThinking) => redactedThinking.Validate(), + (toolUse) => toolUse.Validate(), + (serverToolUse) => serverToolUse.Validate(), + (webSearchToolResult) => webSearchToolResult.Validate() + ); + } + + public virtual bool Equals(ContentBlock? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/ContentBlockParam.cs b/src/Anthropic/Models/Messages/ContentBlockParam.cs index 2f7a6f26..efffb235 100644 --- a/src/Anthropic/Models/Messages/ContentBlockParam.cs +++ b/src/Anthropic/Models/Messages/ContentBlockParam.cs @@ -181,60 +181,210 @@ public ContentBlockParam(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickText(out var value)) { + /// // `value` is of type `TextBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickText([NotNullWhen(true)] out TextBlockParam? value) { value = this.Value as TextBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickImage(out var value)) { + /// // `value` is of type `ImageBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickImage([NotNullWhen(true)] out ImageBlockParam? value) { value = this.Value as ImageBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickDocument(out var value)) { + /// // `value` is of type `DocumentBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickDocument([NotNullWhen(true)] out DocumentBlockParam? value) { value = this.Value as DocumentBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickSearchResult(out var value)) { + /// // `value` is of type `SearchResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickSearchResult([NotNullWhen(true)] out SearchResultBlockParam? value) { value = this.Value as SearchResultBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickThinking(out var value)) { + /// // `value` is of type `ThinkingBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickThinking([NotNullWhen(true)] out ThinkingBlockParam? value) { value = this.Value as ThinkingBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickRedactedThinking(out var value)) { + /// // `value` is of type `RedactedThinkingBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickRedactedThinking([NotNullWhen(true)] out RedactedThinkingBlockParam? value) { value = this.Value as RedactedThinkingBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickToolUse(out var value)) { + /// // `value` is of type `ToolUseBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickToolUse([NotNullWhen(true)] out ToolUseBlockParam? value) { value = this.Value as ToolUseBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickToolResult(out var value)) { + /// // `value` is of type `ToolResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickToolResult([NotNullWhen(true)] out ToolResultBlockParam? value) { value = this.Value as ToolResultBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickServerToolUse(out var value)) { + /// // `value` is of type `ServerToolUseBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickServerToolUse([NotNullWhen(true)] out ServerToolUseBlockParam? value) { value = this.Value as ServerToolUseBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickWebSearchToolResult(out var value)) { + /// // `value` is of type `WebSearchToolResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickWebSearchToolResult( [NotNullWhen(true)] out WebSearchToolResultBlockParam? value ) @@ -243,6 +393,34 @@ public bool TryPickWebSearchToolResult( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (TextBlockParam value) => {...}, + /// (ImageBlockParam value) => {...}, + /// (DocumentBlockParam value) => {...}, + /// (SearchResultBlockParam value) => {...}, + /// (ThinkingBlockParam value) => {...}, + /// (RedactedThinkingBlockParam value) => {...}, + /// (ToolUseBlockParam value) => {...}, + /// (ToolResultBlockParam value) => {...}, + /// (ServerToolUseBlockParam value) => {...}, + /// (WebSearchToolResultBlockParam value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action text, System::Action image, @@ -295,6 +473,35 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (TextBlockParam value) => {...}, + /// (ImageBlockParam value) => {...}, + /// (DocumentBlockParam value) => {...}, + /// (SearchResultBlockParam value) => {...}, + /// (ThinkingBlockParam value) => {...}, + /// (RedactedThinkingBlockParam value) => {...}, + /// (ToolUseBlockParam value) => {...}, + /// (ToolResultBlockParam value) => {...}, + /// (ServerToolUseBlockParam value) => {...}, + /// (WebSearchToolResultBlockParam value) => {...} + /// ); + /// + /// + /// public T Match( System::Func text, System::Func image, @@ -348,6 +555,16 @@ public static implicit operator ContentBlockParam(RedactedThinkingBlockParam val public static implicit operator ContentBlockParam(WebSearchToolResultBlockParam value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -356,6 +573,28 @@ public void Validate() "Data did not match any variant of ContentBlockParam" ); } + this.Switch( + (text) => text.Validate(), + (image) => image.Validate(), + (document) => document.Validate(), + (searchResult) => searchResult.Validate(), + (thinking) => thinking.Validate(), + (redactedThinking) => redactedThinking.Validate(), + (toolUse) => toolUse.Validate(), + (toolResult) => toolResult.Validate(), + (serverToolUse) => serverToolUse.Validate(), + (webSearchToolResult) => webSearchToolResult.Validate() + ); + } + + public virtual bool Equals(ContentBlockParam? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/ContentBlockSource.cs b/src/Anthropic/Models/Messages/ContentBlockSource.cs index 6b65396b..883ed000 100644 --- a/src/Anthropic/Models/Messages/ContentBlockSource.cs +++ b/src/Anthropic/Models/Messages/ContentBlockSource.cs @@ -15,50 +15,17 @@ public sealed record class ContentBlockSource : ModelBase { public required Content Content { - get - { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "content"); } + init { ModelBase.Set(this._rawData, "content", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -78,6 +45,9 @@ public ContentBlockSource() this.Type = JsonSerializer.Deserialize("\"content\""); } + public ContentBlockSource(ContentBlockSource contentBlockSource) + : base(contentBlockSource) { } + public ContentBlockSource(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -93,6 +63,7 @@ public ContentBlockSource(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ContentBlockSource FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -110,6 +81,7 @@ public ContentBlockSource(Content content) class ContentBlockSourceFromRaw : IFromRaw { + /// public ContentBlockSource FromRawUnchecked(IReadOnlyDictionary rawData) => ContentBlockSource.FromRawUnchecked(rawData); } @@ -143,12 +115,42 @@ public Content(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBlockSource(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBlockSource( [NotNullWhen(true)] out IReadOnlyList? value ) @@ -157,6 +159,26 @@ public bool TryPickBlockSource( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action @string, System::Action> contentBlockSourceContent @@ -177,6 +199,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match( System::Func @string, System::Func, T> contentBlockSourceContent @@ -197,6 +240,16 @@ public T Match( public static implicit operator Content(List value) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -204,6 +257,16 @@ public void Validate() throw new AnthropicInvalidDataException("Data did not match any variant of Content"); } } + + public virtual bool Equals(Content? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } } sealed class ContentConverter : JsonConverter diff --git a/src/Anthropic/Models/Messages/ContentBlockSourceContent.cs b/src/Anthropic/Models/Messages/ContentBlockSourceContent.cs index c6f0bf05..e71e0196 100644 --- a/src/Anthropic/Models/Messages/ContentBlockSourceContent.cs +++ b/src/Anthropic/Models/Messages/ContentBlockSourceContent.cs @@ -51,18 +51,68 @@ public ContentBlockSourceContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTextBlockParam(out var value)) { + /// // `value` is of type `TextBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTextBlockParam([NotNullWhen(true)] out TextBlockParam? value) { value = this.Value as TextBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickImageBlockParam(out var value)) { + /// // `value` is of type `ImageBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickImageBlockParam([NotNullWhen(true)] out ImageBlockParam? value) { value = this.Value as ImageBlockParam; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (TextBlockParam value) => {...}, + /// (ImageBlockParam value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action textBlockParam, System::Action imageBlockParam @@ -83,6 +133,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (TextBlockParam value) => {...}, + /// (ImageBlockParam value) => {...} + /// ); + /// + /// + /// public T Match( System::Func textBlockParam, System::Func imageBlockParam @@ -102,6 +173,16 @@ public T Match( public static implicit operator ContentBlockSourceContent(ImageBlockParam value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -110,6 +191,20 @@ public void Validate() "Data did not match any variant of ContentBlockSourceContent" ); } + this.Switch( + (textBlockParam) => textBlockParam.Validate(), + (imageBlockParam) => imageBlockParam.Validate() + ); + } + + public virtual bool Equals(ContentBlockSourceContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/DocumentBlockParam.cs b/src/Anthropic/Models/Messages/DocumentBlockParam.cs index b204f4a6..9d25e512 100644 --- a/src/Anthropic/Models/Messages/DocumentBlockParam.cs +++ b/src/Anthropic/Models/Messages/DocumentBlockParam.cs @@ -14,48 +14,14 @@ public sealed record class DocumentBlockParam : ModelBase { public required Source Source { - get - { - if (!this._rawData.TryGetValue("source", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'source' cannot be null", - new System::ArgumentOutOfRangeException("source", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'source' cannot be null", - new System::ArgumentNullException("source") - ); - } - init - { - this._rawData["source"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "source"); } + init { ModelBase.Set(this._rawData, "source", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -65,80 +31,30 @@ public CacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "cache_control"); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } public CitationsConfigParam? Citations { - get - { - if (!this._rawData.TryGetValue("citations", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["citations"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "citations"); } + init { ModelBase.Set(this._rawData, "citations", value); } } public string? Context { - get - { - if (!this._rawData.TryGetValue("context", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["context"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "context"); } + init { ModelBase.Set(this._rawData, "context", value); } } public string? Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } + /// public override void Validate() { this.Source.Validate(); @@ -162,6 +78,9 @@ public DocumentBlockParam() this.Type = JsonSerializer.Deserialize("\"document\""); } + public DocumentBlockParam(DocumentBlockParam documentBlockParam) + : base(documentBlockParam) { } + public DocumentBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -177,6 +96,7 @@ public DocumentBlockParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static DocumentBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -194,6 +114,7 @@ public DocumentBlockParam(Source source) class DocumentBlockParamFromRaw : IFromRaw { + /// public DocumentBlockParam FromRawUnchecked(IReadOnlyDictionary rawData) => DocumentBlockParam.FromRawUnchecked(rawData); } @@ -278,30 +199,112 @@ public Source(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBase64PDF(out var value)) { + /// // `value` is of type `Base64PDFSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBase64PDF([NotNullWhen(true)] out Base64PDFSource? value) { value = this.Value as Base64PDFSource; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickPlainText(out var value)) { + /// // `value` is of type `PlainTextSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickPlainText([NotNullWhen(true)] out PlainTextSource? value) { value = this.Value as PlainTextSource; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickContentBlock(out var value)) { + /// // `value` is of type `ContentBlockSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickContentBlock([NotNullWhen(true)] out ContentBlockSource? value) { value = this.Value as ContentBlockSource; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickURLPDF(out var value)) { + /// // `value` is of type `URLPDFSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickURLPDF([NotNullWhen(true)] out URLPDFSource? value) { value = this.Value as URLPDFSource; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (Base64PDFSource value) => {...}, + /// (PlainTextSource value) => {...}, + /// (ContentBlockSource value) => {...}, + /// (URLPDFSource value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action base64PDF, System::Action plainText, @@ -328,6 +331,29 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (Base64PDFSource value) => {...}, + /// (PlainTextSource value) => {...}, + /// (ContentBlockSource value) => {...}, + /// (URLPDFSource value) => {...} + /// ); + /// + /// + /// public T Match( System::Func base64PDF, System::Func plainText, @@ -355,12 +381,38 @@ public T Match( public static implicit operator Source(URLPDFSource value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of Source"); } + this.Switch( + (base64PDF) => base64PDF.Validate(), + (plainText) => plainText.Validate(), + (contentBlock) => contentBlock.Validate(), + (urlPDF) => urlPDF.Validate() + ); + } + + public virtual bool Equals(Source? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/ImageBlockParam.cs b/src/Anthropic/Models/Messages/ImageBlockParam.cs index 0e88fa38..b1ad6707 100644 --- a/src/Anthropic/Models/Messages/ImageBlockParam.cs +++ b/src/Anthropic/Models/Messages/ImageBlockParam.cs @@ -14,51 +14,14 @@ public sealed record class ImageBlockParam : ModelBase { public required ImageBlockParamSource Source { - get - { - if (!this._rawData.TryGetValue("source", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'source' cannot be null", - new System::ArgumentOutOfRangeException("source", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'source' cannot be null", - new System::ArgumentNullException("source") - ); - } - init - { - this._rawData["source"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "source"); } + init { ModelBase.Set(this._rawData, "source", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -68,23 +31,12 @@ public CacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "cache_control"); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { this.Source.Validate(); @@ -102,6 +54,9 @@ public ImageBlockParam() this.Type = JsonSerializer.Deserialize("\"image\""); } + public ImageBlockParam(ImageBlockParam imageBlockParam) + : base(imageBlockParam) { } + public ImageBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -117,6 +72,7 @@ public ImageBlockParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ImageBlockParam FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -132,6 +88,7 @@ public ImageBlockParam(ImageBlockParamSource source) class ImageBlockParamFromRaw : IFromRaw { + /// public ImageBlockParam FromRawUnchecked(IReadOnlyDictionary rawData) => ImageBlockParam.FromRawUnchecked(rawData); } @@ -170,18 +127,68 @@ public ImageBlockParamSource(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBase64Image(out var value)) { + /// // `value` is of type `Base64ImageSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBase64Image([NotNullWhen(true)] out Base64ImageSource? value) { value = this.Value as Base64ImageSource; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickURLImage(out var value)) { + /// // `value` is of type `URLImageSource` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickURLImage([NotNullWhen(true)] out URLImageSource? value) { value = this.Value as URLImageSource; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (Base64ImageSource value) => {...}, + /// (URLImageSource value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action base64Image, System::Action urlImage @@ -202,6 +209,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (Base64ImageSource value) => {...}, + /// (URLImageSource value) => {...} + /// ); + /// + /// + /// public T Match( System::Func base64Image, System::Func urlImage @@ -221,6 +249,16 @@ public T Match( public static implicit operator ImageBlockParamSource(URLImageSource value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -229,6 +267,17 @@ public void Validate() "Data did not match any variant of ImageBlockParamSource" ); } + this.Switch((base64Image) => base64Image.Validate(), (urlImage) => urlImage.Validate()); + } + + public virtual bool Equals(ImageBlockParamSource? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/InputJSONDelta.cs b/src/Anthropic/Models/Messages/InputJSONDelta.cs index b1d15491..bed39ff3 100644 --- a/src/Anthropic/Models/Messages/InputJSONDelta.cs +++ b/src/Anthropic/Models/Messages/InputJSONDelta.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class InputJSONDelta : ModelBase { public required string PartialJSON { - get - { - if (!this._rawData.TryGetValue("partial_json", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'partial_json' cannot be null", - new ArgumentOutOfRangeException("partial_json", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'partial_json' cannot be null", - new ArgumentNullException("partial_json") - ); - } - init - { - this._rawData["partial_json"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "partial_json"); } + init { ModelBase.Set(this._rawData, "partial_json", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.PartialJSON; @@ -77,6 +43,9 @@ public InputJSONDelta() this.Type = JsonSerializer.Deserialize("\"input_json_delta\""); } + public InputJSONDelta(InputJSONDelta inputJSONDelta) + : base(inputJSONDelta) { } + public InputJSONDelta(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public InputJSONDelta(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static InputJSONDelta FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -107,6 +77,7 @@ public InputJSONDelta(string partialJSON) class InputJSONDeltaFromRaw : IFromRaw { + /// public InputJSONDelta FromRawUnchecked(IReadOnlyDictionary rawData) => InputJSONDelta.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/Message.cs b/src/Anthropic/Models/Messages/Message.cs index 133b4f95..5dd57543 100644 --- a/src/Anthropic/Models/Messages/Message.cs +++ b/src/Anthropic/Models/Messages/Message.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,27 +18,8 @@ public sealed record class Message : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -66,30 +46,8 @@ public required string ID /// public required IReadOnlyList Content { - get - { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "content"); } + init { ModelBase.Set(this._rawData, "content", value); } } /// @@ -98,26 +56,8 @@ public required IReadOnlyList Content /// public required ApiEnum Model { - get - { - if (!this._rawData.TryGetValue("model", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'model' cannot be null", - new ArgumentOutOfRangeException("model", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["model"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "model"); } + init { ModelBase.Set(this._rawData, "model", value); } } /// @@ -127,23 +67,8 @@ public required ApiEnum Model /// public JsonElement Role { - get - { - if (!this._rawData.TryGetValue("role", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'role' cannot be null", - new ArgumentOutOfRangeException("role", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["role"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "role"); } + init { ModelBase.Set(this._rawData, "role", value); } } /// @@ -164,21 +89,12 @@ public required ApiEnum? StopReason { get { - if (!this._rawData.TryGetValue("stop_reason", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["stop_reason"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawData, + "stop_reason" ); } + init { ModelBase.Set(this._rawData, "stop_reason", value); } } /// @@ -189,20 +105,8 @@ public required ApiEnum? StopReason /// public required string? StopSequence { - get - { - if (!this._rawData.TryGetValue("stop_sequence", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["stop_sequence"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "stop_sequence"); } + init { ModelBase.Set(this._rawData, "stop_sequence", value); } } /// @@ -212,23 +116,8 @@ public required string? StopSequence /// public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -250,29 +139,11 @@ public JsonElement Type /// public required Usage Usage { - get - { - if (!this._rawData.TryGetValue("usage", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'usage' cannot be null", - new ArgumentOutOfRangeException("usage", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'usage' cannot be null", - new ArgumentNullException("usage") - ); - } - init - { - this._rawData["usage"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "usage"); } + init { ModelBase.Set(this._rawData, "usage", value); } } + /// public override void Validate() { _ = this.ID; @@ -310,6 +181,9 @@ public Message() this.Type = JsonSerializer.Deserialize("\"message\""); } + public Message(Message message) + : base(message) { } + public Message(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -326,6 +200,7 @@ public Message(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static Message FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -334,6 +209,7 @@ public static Message FromRawUnchecked(IReadOnlyDictionary class MessageFromRaw : IFromRaw { + /// public Message FromRawUnchecked(IReadOnlyDictionary rawData) => Message.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/MessageCountTokensParams.cs b/src/Anthropic/Models/Messages/MessageCountTokensParams.cs index 53c66fef..f9b474ef 100644 --- a/src/Anthropic/Models/Messages/MessageCountTokensParams.cs +++ b/src/Anthropic/Models/Messages/MessageCountTokensParams.cs @@ -81,30 +81,8 @@ public IReadOnlyDictionary RawBodyData /// public required IReadOnlyList Messages { - get - { - if (!this._rawBodyData.TryGetValue("messages", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'messages' cannot be null", - new System::ArgumentOutOfRangeException("messages", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'messages' cannot be null", - new System::ArgumentNullException("messages") - ); - } - init - { - this._rawBodyData["messages"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawBodyData, "messages"); } + init { ModelBase.Set(this._rawBodyData, "messages", value); } } /// @@ -113,26 +91,8 @@ public required IReadOnlyList Messages /// public required ApiEnum Model { - get - { - if (!this._rawBodyData.TryGetValue("model", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'model' cannot be null", - new System::ArgumentOutOfRangeException("model", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawBodyData["model"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawBodyData, "model"); } + init { ModelBase.Set(this._rawBodyData, "model", value); } } /// @@ -141,14 +101,14 @@ public required ApiEnum Model /// A system prompt is a way of providing context and instructions to Claude, /// such as specifying a particular goal or role. See our [guide to system prompts](https://docs.claude.com/en/docs/system-prompts). /// - public System1? System + public MessageCountTokensParamsSystem? System { get { - if (!this._rawBodyData.TryGetValue("system", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); + return ModelBase.GetNullableClass( + this.RawBodyData, + "system" + ); } init { @@ -157,10 +117,7 @@ public System1? System return; } - this._rawBodyData["system"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "system", value); } } @@ -178,13 +135,7 @@ public ThinkingConfigParam? Thinking { get { - if (!this._rawBodyData.TryGetValue("thinking", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawBodyData, "thinking"); } init { @@ -193,10 +144,7 @@ public ThinkingConfigParam? Thinking return; } - this._rawBodyData["thinking"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "thinking", value); } } @@ -206,13 +154,7 @@ public ThinkingConfigParam? Thinking /// public ToolChoice? ToolChoice { - get - { - if (!this._rawBodyData.TryGetValue("tool_choice", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawBodyData, "tool_choice"); } init { if (value == null) @@ -220,10 +162,7 @@ public ToolChoice? ToolChoice return; } - this._rawBodyData["tool_choice"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "tool_choice", value); } } @@ -278,12 +217,9 @@ public IReadOnlyList? Tools { get { - if (!this._rawBodyData.TryGetValue("tools", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawBodyData, + "tools" ); } init @@ -293,15 +229,18 @@ public IReadOnlyList? Tools return; } - this._rawBodyData["tools"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "tools", value); } } public MessageCountTokensParams() { } + public MessageCountTokensParams(MessageCountTokensParams messageCountTokensParams) + : base(messageCountTokensParams) + { + this._rawBodyData = [.. messageCountTokensParams._rawBodyData]; + } + public MessageCountTokensParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, @@ -327,6 +266,7 @@ FrozenDictionary rawBodyData } #pragma warning restore CS8618 + /// public static MessageCountTokensParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, @@ -371,8 +311,8 @@ internal override void AddHeadersToRequest(HttpRequestMessage request, ClientOpt /// A system prompt is a way of providing context and instructions to Claude, /// such as specifying a particular goal or role. See our [guide to system prompts](https://docs.claude.com/en/docs/system-prompts). /// -[JsonConverter(typeof(System1Converter))] -public record class System1 +[JsonConverter(typeof(MessageCountTokensParamsSystemConverter))] +public record class MessageCountTokensParamsSystem { public object? Value { get; } = null; @@ -383,35 +323,88 @@ public JsonElement Json get { return this._json ??= JsonSerializer.SerializeToElement(this.Value); } } - public System1(string value, JsonElement? json = null) + public MessageCountTokensParamsSystem(string value, JsonElement? json = null) { this.Value = value; this._json = json; } - public System1(IReadOnlyList value, JsonElement? json = null) + public MessageCountTokensParamsSystem( + IReadOnlyList value, + JsonElement? json = null + ) { this.Value = ImmutableArray.ToImmutableArray(value); this._json = json; } - public System1(JsonElement json) + public MessageCountTokensParamsSystem(JsonElement json) { this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTextBlockParams(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTextBlockParams([NotNullWhen(true)] out IReadOnlyList? value) { value = this.Value as IReadOnlyList; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action @string, System::Action> textBlockParams @@ -427,11 +420,32 @@ public void Switch( break; default: throw new AnthropicInvalidDataException( - "Data did not match any variant of System1" + "Data did not match any variant of MessageCountTokensParamsSystem" ); } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match( System::Func @string, System::Func, T> textBlockParams @@ -442,28 +456,50 @@ public T Match( string value => @string(value), IReadOnlyList value => textBlockParams(value), _ => throw new AnthropicInvalidDataException( - "Data did not match any variant of System1" + "Data did not match any variant of MessageCountTokensParamsSystem" ), }; } - public static implicit operator System1(string value) => new(value); + public static implicit operator MessageCountTokensParamsSystem(string value) => new(value); - public static implicit operator System1(List value) => + public static implicit operator MessageCountTokensParamsSystem(List value) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { - throw new AnthropicInvalidDataException("Data did not match any variant of System1"); + throw new AnthropicInvalidDataException( + "Data did not match any variant of MessageCountTokensParamsSystem" + ); } } + + public virtual bool Equals(MessageCountTokensParamsSystem? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } } -sealed class System1Converter : JsonConverter +sealed class MessageCountTokensParamsSystemConverter : JsonConverter { - public override System1? Read( + public override MessageCountTokensParamsSystem? Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -499,7 +535,11 @@ JsonSerializerOptions options return new(json); } - public override void Write(Utf8JsonWriter writer, System1 value, JsonSerializerOptions options) + public override void Write( + Utf8JsonWriter writer, + MessageCountTokensParamsSystem value, + JsonSerializerOptions options + ) { JsonSerializer.Serialize(writer, value.Json, options); } diff --git a/src/Anthropic/Models/Messages/MessageCountTokensTool.cs b/src/Anthropic/Models/Messages/MessageCountTokensTool.cs index 0aaba3d8..8e014ba1 100644 --- a/src/Anthropic/Models/Messages/MessageCountTokensTool.cs +++ b/src/Anthropic/Models/Messages/MessageCountTokensTool.cs @@ -74,42 +74,156 @@ public MessageCountTokensTool(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTool(out var value)) { + /// // `value` is of type `Tool` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTool([NotNullWhen(true)] out Tool? value) { value = this.Value as Tool; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickToolBash20250124(out var value)) { + /// // `value` is of type `ToolBash20250124` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickToolBash20250124([NotNullWhen(true)] out ToolBash20250124? value) { value = this.Value as ToolBash20250124; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickToolTextEditor20250124(out var value)) { + /// // `value` is of type `ToolTextEditor20250124` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickToolTextEditor20250124([NotNullWhen(true)] out ToolTextEditor20250124? value) { value = this.Value as ToolTextEditor20250124; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickToolTextEditor20250429(out var value)) { + /// // `value` is of type `ToolTextEditor20250429` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickToolTextEditor20250429([NotNullWhen(true)] out ToolTextEditor20250429? value) { value = this.Value as ToolTextEditor20250429; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickToolTextEditor20250728(out var value)) { + /// // `value` is of type `ToolTextEditor20250728` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickToolTextEditor20250728([NotNullWhen(true)] out ToolTextEditor20250728? value) { value = this.Value as ToolTextEditor20250728; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickWebSearchTool20250305(out var value)) { + /// // `value` is of type `WebSearchTool20250305` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickWebSearchTool20250305([NotNullWhen(true)] out WebSearchTool20250305? value) { value = this.Value as WebSearchTool20250305; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (Tool value) => {...}, + /// (ToolBash20250124 value) => {...}, + /// (ToolTextEditor20250124 value) => {...}, + /// (ToolTextEditor20250429 value) => {...}, + /// (ToolTextEditor20250728 value) => {...}, + /// (WebSearchTool20250305 value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action tool, System::Action toolBash20250124, @@ -146,6 +260,31 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (Tool value) => {...}, + /// (ToolBash20250124 value) => {...}, + /// (ToolTextEditor20250124 value) => {...}, + /// (ToolTextEditor20250429 value) => {...}, + /// (ToolTextEditor20250728 value) => {...}, + /// (WebSearchTool20250305 value) => {...} + /// ); + /// + /// + /// public T Match( System::Func tool, System::Func toolBash20250124, @@ -185,6 +324,16 @@ public static implicit operator MessageCountTokensTool(ToolTextEditor20250728 va public static implicit operator MessageCountTokensTool(WebSearchTool20250305 value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -193,6 +342,24 @@ public void Validate() "Data did not match any variant of MessageCountTokensTool" ); } + this.Switch( + (tool) => tool.Validate(), + (toolBash20250124) => toolBash20250124.Validate(), + (toolTextEditor20250124) => toolTextEditor20250124.Validate(), + (toolTextEditor20250429) => toolTextEditor20250429.Validate(), + (toolTextEditor20250728) => toolTextEditor20250728.Validate(), + (webSearchTool20250305) => webSearchTool20250305.Validate() + ); + } + + public virtual bool Equals(MessageCountTokensTool? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/MessageCreateParams.cs b/src/Anthropic/Models/Messages/MessageCreateParams.cs index 0033606b..48608afb 100644 --- a/src/Anthropic/Models/Messages/MessageCreateParams.cs +++ b/src/Anthropic/Models/Messages/MessageCreateParams.cs @@ -39,26 +39,8 @@ public IReadOnlyDictionary RawBodyData /// public required long MaxTokens { - get - { - if (!this._rawBodyData.TryGetValue("max_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'max_tokens' cannot be null", - new System::ArgumentOutOfRangeException( - "max_tokens", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawBodyData["max_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawBodyData, "max_tokens"); } + init { ModelBase.Set(this._rawBodyData, "max_tokens", value); } } /// @@ -114,30 +96,8 @@ public required long MaxTokens /// public required IReadOnlyList Messages { - get - { - if (!this._rawBodyData.TryGetValue("messages", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'messages' cannot be null", - new System::ArgumentOutOfRangeException("messages", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'messages' cannot be null", - new System::ArgumentNullException("messages") - ); - } - init - { - this._rawBodyData["messages"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawBodyData, "messages"); } + init { ModelBase.Set(this._rawBodyData, "messages", value); } } /// @@ -146,26 +106,8 @@ public required IReadOnlyList Messages /// public required ApiEnum Model { - get - { - if (!this._rawBodyData.TryGetValue("model", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'model' cannot be null", - new System::ArgumentOutOfRangeException("model", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawBodyData["model"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawBodyData, "model"); } + init { ModelBase.Set(this._rawBodyData, "model", value); } } /// @@ -173,13 +115,7 @@ public required ApiEnum Model /// public Metadata? Metadata { - get - { - if (!this._rawBodyData.TryGetValue("metadata", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawBodyData, "metadata"); } init { if (value == null) @@ -187,10 +123,7 @@ public Metadata? Metadata return; } - this._rawBodyData["metadata"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "metadata", value); } } @@ -205,12 +138,9 @@ public ApiEnum? ServiceTier { get { - if (!this._rawBodyData.TryGetValue("service_tier", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawBodyData, + "service_tier" ); } init @@ -220,10 +150,7 @@ public ApiEnum? ServiceTier return; } - this._rawBodyData["service_tier"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "service_tier", value); } } @@ -241,13 +168,7 @@ public ApiEnum? ServiceTier /// public IReadOnlyList? StopSequences { - get - { - if (!this._rawBodyData.TryGetValue("stop_sequences", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass>(this.RawBodyData, "stop_sequences"); } init { if (value == null) @@ -255,10 +176,7 @@ public IReadOnlyList? StopSequences return; } - this._rawBodyData["stop_sequences"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "stop_sequences", value); } } @@ -268,14 +186,14 @@ public IReadOnlyList? StopSequences /// A system prompt is a way of providing context and instructions to Claude, /// such as specifying a particular goal or role. See our [guide to system prompts](https://docs.claude.com/en/docs/system-prompts). /// - public SystemModel? System + public MessageCreateParamsSystem? System { get { - if (!this._rawBodyData.TryGetValue("system", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); + return ModelBase.GetNullableClass( + this.RawBodyData, + "system" + ); } init { @@ -284,10 +202,7 @@ public SystemModel? System return; } - this._rawBodyData["system"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "system", value); } } @@ -303,13 +218,7 @@ public SystemModel? System /// public double? Temperature { - get - { - if (!this._rawBodyData.TryGetValue("temperature", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawBodyData, "temperature"); } init { if (value == null) @@ -317,10 +226,7 @@ public double? Temperature return; } - this._rawBodyData["temperature"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "temperature", value); } } @@ -338,13 +244,7 @@ public ThinkingConfigParam? Thinking { get { - if (!this._rawBodyData.TryGetValue("thinking", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawBodyData, "thinking"); } init { @@ -353,10 +253,7 @@ public ThinkingConfigParam? Thinking return; } - this._rawBodyData["thinking"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "thinking", value); } } @@ -366,13 +263,7 @@ public ThinkingConfigParam? Thinking /// public ToolChoice? ToolChoice { - get - { - if (!this._rawBodyData.TryGetValue("tool_choice", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawBodyData, "tool_choice"); } init { if (value == null) @@ -380,10 +271,7 @@ public ToolChoice? ToolChoice return; } - this._rawBodyData["tool_choice"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "tool_choice", value); } } @@ -436,16 +324,7 @@ public ToolChoice? ToolChoice /// public IReadOnlyList? Tools { - get - { - if (!this._rawBodyData.TryGetValue("tools", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawBodyData, "tools"); } init { if (value == null) @@ -453,10 +332,7 @@ public IReadOnlyList? Tools return; } - this._rawBodyData["tools"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "tools", value); } } @@ -470,13 +346,7 @@ public IReadOnlyList? Tools /// public long? TopK { - get - { - if (!this._rawBodyData.TryGetValue("top_k", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawBodyData, "top_k"); } init { if (value == null) @@ -484,10 +354,7 @@ public long? TopK return; } - this._rawBodyData["top_k"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "top_k", value); } } @@ -503,13 +370,7 @@ public long? TopK /// public double? TopP { - get - { - if (!this._rawBodyData.TryGetValue("top_p", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawBodyData, "top_p"); } init { if (value == null) @@ -517,15 +378,18 @@ public double? TopP return; } - this._rawBodyData["top_p"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawBodyData, "top_p", value); } } public MessageCreateParams() { } + public MessageCreateParams(MessageCreateParams messageCreateParams) + : base(messageCreateParams) + { + this._rawBodyData = [.. messageCreateParams._rawBodyData]; + } + public MessageCreateParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, @@ -551,6 +415,7 @@ FrozenDictionary rawBodyData } #pragma warning restore CS8618 + /// public static MessageCreateParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData, @@ -644,8 +509,8 @@ JsonSerializerOptions options /// A system prompt is a way of providing context and instructions to Claude, /// such as specifying a particular goal or role. See our [guide to system prompts](https://docs.claude.com/en/docs/system-prompts). /// -[JsonConverter(typeof(SystemModelConverter))] -public record class SystemModel +[JsonConverter(typeof(MessageCreateParamsSystemConverter))] +public record class MessageCreateParamsSystem { public object? Value { get; } = null; @@ -656,35 +521,85 @@ public JsonElement Json get { return this._json ??= JsonSerializer.SerializeToElement(this.Value); } } - public SystemModel(string value, JsonElement? json = null) + public MessageCreateParamsSystem(string value, JsonElement? json = null) { this.Value = value; this._json = json; } - public SystemModel(IReadOnlyList value, JsonElement? json = null) + public MessageCreateParamsSystem(IReadOnlyList value, JsonElement? json = null) { this.Value = ImmutableArray.ToImmutableArray(value); this._json = json; } - public SystemModel(JsonElement json) + public MessageCreateParamsSystem(JsonElement json) { this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTextBlockParams(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTextBlockParams([NotNullWhen(true)] out IReadOnlyList? value) { value = this.Value as IReadOnlyList; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action @string, System::Action> textBlockParams @@ -700,11 +615,32 @@ public void Switch( break; default: throw new AnthropicInvalidDataException( - "Data did not match any variant of SystemModel" + "Data did not match any variant of MessageCreateParamsSystem" ); } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match( System::Func @string, System::Func, T> textBlockParams @@ -715,30 +651,50 @@ public T Match( string value => @string(value), IReadOnlyList value => textBlockParams(value), _ => throw new AnthropicInvalidDataException( - "Data did not match any variant of SystemModel" + "Data did not match any variant of MessageCreateParamsSystem" ), }; } - public static implicit operator SystemModel(string value) => new(value); + public static implicit operator MessageCreateParamsSystem(string value) => new(value); - public static implicit operator SystemModel(List value) => + public static implicit operator MessageCreateParamsSystem(List value) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException( - "Data did not match any variant of SystemModel" + "Data did not match any variant of MessageCreateParamsSystem" ); } } + + public virtual bool Equals(MessageCreateParamsSystem? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } } -sealed class SystemModelConverter : JsonConverter +sealed class MessageCreateParamsSystemConverter : JsonConverter { - public override SystemModel? Read( + public override MessageCreateParamsSystem? Read( ref Utf8JsonReader reader, System::Type typeToConvert, JsonSerializerOptions options @@ -776,7 +732,7 @@ JsonSerializerOptions options public override void Write( Utf8JsonWriter writer, - SystemModel value, + MessageCreateParamsSystem value, JsonSerializerOptions options ) { diff --git a/src/Anthropic/Models/Messages/MessageDeltaUsage.cs b/src/Anthropic/Models/Messages/MessageDeltaUsage.cs index e732ffeb..e01acdd7 100644 --- a/src/Anthropic/Models/Messages/MessageDeltaUsage.cs +++ b/src/Anthropic/Models/Messages/MessageDeltaUsage.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Messages; @@ -19,18 +17,9 @@ public required long? CacheCreationInputTokens { get { - if (!this._rawData.TryGetValue("cache_creation_input_tokens", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["cache_creation_input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableStruct(this.RawData, "cache_creation_input_tokens"); } + init { ModelBase.Set(this._rawData, "cache_creation_input_tokens", value); } } /// @@ -38,20 +27,8 @@ public required long? CacheCreationInputTokens /// public required long? CacheReadInputTokens { - get - { - if (!this._rawData.TryGetValue("cache_read_input_tokens", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["cache_read_input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "cache_read_input_tokens"); } + init { ModelBase.Set(this._rawData, "cache_read_input_tokens", value); } } /// @@ -59,20 +36,8 @@ public required long? CacheReadInputTokens /// public required long? InputTokens { - get - { - if (!this._rawData.TryGetValue("input_tokens", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "input_tokens"); } + init { ModelBase.Set(this._rawData, "input_tokens", value); } } /// @@ -80,23 +45,8 @@ public required long? InputTokens /// public required long OutputTokens { - get - { - if (!this._rawData.TryGetValue("output_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'output_tokens' cannot be null", - new ArgumentOutOfRangeException("output_tokens", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["output_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "output_tokens"); } + init { ModelBase.Set(this._rawData, "output_tokens", value); } } /// @@ -104,25 +54,11 @@ public required long OutputTokens /// public required ServerToolUsage? ServerToolUse { - get - { - if (!this._rawData.TryGetValue("server_tool_use", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["server_tool_use"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "server_tool_use"); } + init { ModelBase.Set(this._rawData, "server_tool_use", value); } } + /// public override void Validate() { _ = this.CacheCreationInputTokens; @@ -134,6 +70,9 @@ public override void Validate() public MessageDeltaUsage() { } + public MessageDeltaUsage(MessageDeltaUsage messageDeltaUsage) + : base(messageDeltaUsage) { } + public MessageDeltaUsage(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -147,6 +86,7 @@ public MessageDeltaUsage(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static MessageDeltaUsage FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -157,6 +97,7 @@ IReadOnlyDictionary rawData class MessageDeltaUsageFromRaw : IFromRaw { + /// public MessageDeltaUsage FromRawUnchecked(IReadOnlyDictionary rawData) => MessageDeltaUsage.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/MessageParam.cs b/src/Anthropic/Models/Messages/MessageParam.cs index b4673145..98cd73e3 100644 --- a/src/Anthropic/Models/Messages/MessageParam.cs +++ b/src/Anthropic/Models/Messages/MessageParam.cs @@ -15,56 +15,17 @@ public sealed record class MessageParam : ModelBase { public required MessageParamContent Content { - get - { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new System::ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "content"); } + init { ModelBase.Set(this._rawData, "content", value); } } public required ApiEnum Role { - get - { - if (!this._rawData.TryGetValue("role", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'role' cannot be null", - new System::ArgumentOutOfRangeException("role", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["role"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "role"); } + init { ModelBase.Set(this._rawData, "role", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -73,6 +34,9 @@ public override void Validate() public MessageParam() { } + public MessageParam(MessageParam messageParam) + : base(messageParam) { } + public MessageParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -86,6 +50,7 @@ public MessageParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static MessageParam FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -94,6 +59,7 @@ public static MessageParam FromRawUnchecked(IReadOnlyDictionary { + /// public MessageParam FromRawUnchecked(IReadOnlyDictionary rawData) => MessageParam.FromRawUnchecked(rawData); } @@ -127,12 +93,42 @@ public MessageParamContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickContentBlockParams(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickContentBlockParams( [NotNullWhen(true)] out IReadOnlyList? value ) @@ -141,6 +137,26 @@ public bool TryPickContentBlockParams( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action @string, System::Action> contentBlockParams @@ -161,6 +177,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match( System::Func @string, System::Func, T> contentBlockParams @@ -181,6 +218,16 @@ public T Match( public static implicit operator MessageParamContent(List value) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -190,6 +237,16 @@ public void Validate() ); } } + + public virtual bool Equals(MessageParamContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } } sealed class MessageParamContentConverter : JsonConverter diff --git a/src/Anthropic/Models/Messages/MessageTokensCount.cs b/src/Anthropic/Models/Messages/MessageTokensCount.cs index b1aa7383..c884809c 100644 --- a/src/Anthropic/Models/Messages/MessageTokensCount.cs +++ b/src/Anthropic/Models/Messages/MessageTokensCount.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Messages; @@ -18,25 +16,11 @@ public sealed record class MessageTokensCount : ModelBase /// public required long InputTokens { - get - { - if (!this._rawData.TryGetValue("input_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input_tokens' cannot be null", - new ArgumentOutOfRangeException("input_tokens", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "input_tokens"); } + init { ModelBase.Set(this._rawData, "input_tokens", value); } } + /// public override void Validate() { _ = this.InputTokens; @@ -44,6 +28,9 @@ public override void Validate() public MessageTokensCount() { } + public MessageTokensCount(MessageTokensCount messageTokensCount) + : base(messageTokensCount) { } + public MessageTokensCount(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -57,6 +44,7 @@ public MessageTokensCount(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static MessageTokensCount FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -74,6 +62,7 @@ public MessageTokensCount(long inputTokens) class MessageTokensCountFromRaw : IFromRaw { + /// public MessageTokensCount FromRawUnchecked(IReadOnlyDictionary rawData) => MessageTokensCount.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/Metadata.cs b/src/Anthropic/Models/Messages/Metadata.cs index 9cd19d9f..5572e322 100644 --- a/src/Anthropic/Models/Messages/Metadata.cs +++ b/src/Anthropic/Models/Messages/Metadata.cs @@ -19,22 +19,11 @@ public sealed record class Metadata : ModelBase /// public string? UserID { - get - { - if (!this._rawData.TryGetValue("user_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["user_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "user_id"); } + init { ModelBase.Set(this._rawData, "user_id", value); } } + /// public override void Validate() { _ = this.UserID; @@ -42,6 +31,9 @@ public override void Validate() public Metadata() { } + public Metadata(Metadata metadata) + : base(metadata) { } + public Metadata(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -55,6 +47,7 @@ public Metadata(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static Metadata FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -63,6 +56,7 @@ public static Metadata FromRawUnchecked(IReadOnlyDictionary class MetadataFromRaw : IFromRaw { + /// public Metadata FromRawUnchecked(IReadOnlyDictionary rawData) => Metadata.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/PlainTextSource.cs b/src/Anthropic/Models/Messages/PlainTextSource.cs index 2b1113e6..500219ad 100644 --- a/src/Anthropic/Models/Messages/PlainTextSource.cs +++ b/src/Anthropic/Models/Messages/PlainTextSource.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,71 +13,23 @@ public sealed record class PlainTextSource : ModelBase { public required string Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } public JsonElement MediaType { - get - { - if (!this._rawData.TryGetValue("media_type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'media_type' cannot be null", - new ArgumentOutOfRangeException("media_type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["media_type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "media_type"); } + init { ModelBase.Set(this._rawData, "media_type", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Data; @@ -103,6 +54,9 @@ public PlainTextSource() this.Type = JsonSerializer.Deserialize("\"text\""); } + public PlainTextSource(PlainTextSource plainTextSource) + : base(plainTextSource) { } + public PlainTextSource(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -119,6 +73,7 @@ public PlainTextSource(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static PlainTextSource FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -134,6 +89,7 @@ public PlainTextSource(string data) class PlainTextSourceFromRaw : IFromRaw { + /// public PlainTextSource FromRawUnchecked(IReadOnlyDictionary rawData) => PlainTextSource.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/RawContentBlockDelta.cs b/src/Anthropic/Models/Messages/RawContentBlockDelta.cs index 6064cada..0272f80e 100644 --- a/src/Anthropic/Models/Messages/RawContentBlockDelta.cs +++ b/src/Anthropic/Models/Messages/RawContentBlockDelta.cs @@ -67,36 +67,134 @@ public RawContentBlockDelta(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickText(out var value)) { + /// // `value` is of type `TextDelta` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickText([NotNullWhen(true)] out TextDelta? value) { value = this.Value as TextDelta; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickInputJSON(out var value)) { + /// // `value` is of type `InputJSONDelta` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickInputJSON([NotNullWhen(true)] out InputJSONDelta? value) { value = this.Value as InputJSONDelta; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitations(out var value)) { + /// // `value` is of type `CitationsDelta` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitations([NotNullWhen(true)] out CitationsDelta? value) { value = this.Value as CitationsDelta; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickThinking(out var value)) { + /// // `value` is of type `ThinkingDelta` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickThinking([NotNullWhen(true)] out ThinkingDelta? value) { value = this.Value as ThinkingDelta; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickSignature(out var value)) { + /// // `value` is of type `SignatureDelta` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickSignature([NotNullWhen(true)] out SignatureDelta? value) { value = this.Value as SignatureDelta; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (TextDelta value) => {...}, + /// (InputJSONDelta value) => {...}, + /// (CitationsDelta value) => {...}, + /// (ThinkingDelta value) => {...}, + /// (SignatureDelta value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action text, System::Action inputJSON, @@ -129,6 +227,30 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (TextDelta value) => {...}, + /// (InputJSONDelta value) => {...}, + /// (CitationsDelta value) => {...}, + /// (ThinkingDelta value) => {...}, + /// (SignatureDelta value) => {...} + /// ); + /// + /// + /// public T Match( System::Func text, System::Func inputJSON, @@ -160,6 +282,16 @@ public T Match( public static implicit operator RawContentBlockDelta(SignatureDelta value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -168,6 +300,23 @@ public void Validate() "Data did not match any variant of RawContentBlockDelta" ); } + this.Switch( + (text) => text.Validate(), + (inputJSON) => inputJSON.Validate(), + (citations) => citations.Validate(), + (thinking) => thinking.Validate(), + (signature) => signature.Validate() + ); + } + + public virtual bool Equals(RawContentBlockDelta? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/RawContentBlockDeltaEvent.cs b/src/Anthropic/Models/Messages/RawContentBlockDeltaEvent.cs index 6167f3d2..d4a805c9 100644 --- a/src/Anthropic/Models/Messages/RawContentBlockDeltaEvent.cs +++ b/src/Anthropic/Models/Messages/RawContentBlockDeltaEvent.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,74 +13,23 @@ public sealed record class RawContentBlockDeltaEvent : ModelBase { public required RawContentBlockDelta Delta { - get - { - if (!this._rawData.TryGetValue("delta", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'delta' cannot be null", - new ArgumentOutOfRangeException("delta", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'delta' cannot be null", - new ArgumentNullException("delta") - ); - } - init - { - this._rawData["delta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "delta"); } + init { ModelBase.Set(this._rawData, "delta", value); } } public required long Index { - get - { - if (!this._rawData.TryGetValue("index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'index' cannot be null", - new ArgumentOutOfRangeException("index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "index"); } + init { ModelBase.Set(this._rawData, "index", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Delta.Validate(); @@ -102,6 +50,9 @@ public RawContentBlockDeltaEvent() this.Type = JsonSerializer.Deserialize("\"content_block_delta\""); } + public RawContentBlockDeltaEvent(RawContentBlockDeltaEvent rawContentBlockDeltaEvent) + : base(rawContentBlockDeltaEvent) { } + public RawContentBlockDeltaEvent(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -117,6 +68,7 @@ public RawContentBlockDeltaEvent(IReadOnlyDictionary rawDat } #pragma warning restore CS8618 + /// public static RawContentBlockDeltaEvent FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -127,6 +79,7 @@ IReadOnlyDictionary rawData class RawContentBlockDeltaEventFromRaw : IFromRaw { + /// public RawContentBlockDeltaEvent FromRawUnchecked( IReadOnlyDictionary rawData ) => RawContentBlockDeltaEvent.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/RawContentBlockStartEvent.cs b/src/Anthropic/Models/Messages/RawContentBlockStartEvent.cs index ab104873..39cfc5f6 100644 --- a/src/Anthropic/Models/Messages/RawContentBlockStartEvent.cs +++ b/src/Anthropic/Models/Messages/RawContentBlockStartEvent.cs @@ -16,75 +16,27 @@ public required RawContentBlockStartEventContentBlock ContentBlock { get { - if (!this._rawData.TryGetValue("content_block", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content_block' cannot be null", - new System::ArgumentOutOfRangeException( - "content_block", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content_block' cannot be null", - new System::ArgumentNullException("content_block") - ); - } - init - { - this._rawData["content_block"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content_block" ); } + init { ModelBase.Set(this._rawData, "content_block", value); } } public required long Index { - get - { - if (!this._rawData.TryGetValue("index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'index' cannot be null", - new System::ArgumentOutOfRangeException("index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "index"); } + init { ModelBase.Set(this._rawData, "index", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.ContentBlock.Validate(); @@ -105,6 +57,9 @@ public RawContentBlockStartEvent() this.Type = JsonSerializer.Deserialize("\"content_block_start\""); } + public RawContentBlockStartEvent(RawContentBlockStartEvent rawContentBlockStartEvent) + : base(rawContentBlockStartEvent) { } + public RawContentBlockStartEvent(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -120,6 +75,7 @@ public RawContentBlockStartEvent(IReadOnlyDictionary rawDat } #pragma warning restore CS8618 + /// public static RawContentBlockStartEvent FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -130,6 +86,7 @@ IReadOnlyDictionary rawData class RawContentBlockStartEventFromRaw : IFromRaw { + /// public RawContentBlockStartEvent FromRawUnchecked( IReadOnlyDictionary rawData ) => RawContentBlockStartEvent.FromRawUnchecked(rawData); @@ -224,42 +181,156 @@ public RawContentBlockStartEventContentBlock(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickText(out var value)) { + /// // `value` is of type `TextBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickText([NotNullWhen(true)] out TextBlock? value) { value = this.Value as TextBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickThinking(out var value)) { + /// // `value` is of type `ThinkingBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickThinking([NotNullWhen(true)] out ThinkingBlock? value) { value = this.Value as ThinkingBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickRedactedThinking(out var value)) { + /// // `value` is of type `RedactedThinkingBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickRedactedThinking([NotNullWhen(true)] out RedactedThinkingBlock? value) { value = this.Value as RedactedThinkingBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickToolUse(out var value)) { + /// // `value` is of type `ToolUseBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickToolUse([NotNullWhen(true)] out ToolUseBlock? value) { value = this.Value as ToolUseBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickServerToolUse(out var value)) { + /// // `value` is of type `ServerToolUseBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickServerToolUse([NotNullWhen(true)] out ServerToolUseBlock? value) { value = this.Value as ServerToolUseBlock; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickWebSearchToolResult(out var value)) { + /// // `value` is of type `WebSearchToolResultBlock` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickWebSearchToolResult([NotNullWhen(true)] out WebSearchToolResultBlock? value) { value = this.Value as WebSearchToolResultBlock; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (TextBlock value) => {...}, + /// (ThinkingBlock value) => {...}, + /// (RedactedThinkingBlock value) => {...}, + /// (ToolUseBlock value) => {...}, + /// (ServerToolUseBlock value) => {...}, + /// (WebSearchToolResultBlock value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action text, System::Action thinking, @@ -296,6 +367,31 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (TextBlock value) => {...}, + /// (ThinkingBlock value) => {...}, + /// (RedactedThinkingBlock value) => {...}, + /// (ToolUseBlock value) => {...}, + /// (ServerToolUseBlock value) => {...}, + /// (WebSearchToolResultBlock value) => {...} + /// ); + /// + /// + /// public T Match( System::Func text, System::Func thinking, @@ -340,6 +436,16 @@ public static implicit operator RawContentBlockStartEventContentBlock( WebSearchToolResultBlock value ) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -348,6 +454,24 @@ public void Validate() "Data did not match any variant of RawContentBlockStartEventContentBlock" ); } + this.Switch( + (text) => text.Validate(), + (thinking) => thinking.Validate(), + (redactedThinking) => redactedThinking.Validate(), + (toolUse) => toolUse.Validate(), + (serverToolUse) => serverToolUse.Validate(), + (webSearchToolResult) => webSearchToolResult.Validate() + ); + } + + public virtual bool Equals(RawContentBlockStartEventContentBlock? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/RawContentBlockStopEvent.cs b/src/Anthropic/Models/Messages/RawContentBlockStopEvent.cs index 4905a404..84405e14 100644 --- a/src/Anthropic/Models/Messages/RawContentBlockStopEvent.cs +++ b/src/Anthropic/Models/Messages/RawContentBlockStopEvent.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,46 +13,17 @@ public sealed record class RawContentBlockStopEvent : ModelBase { public required long Index { - get - { - if (!this._rawData.TryGetValue("index", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'index' cannot be null", - new ArgumentOutOfRangeException("index", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["index"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "index"); } + init { ModelBase.Set(this._rawData, "index", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Index; @@ -73,6 +43,9 @@ public RawContentBlockStopEvent() this.Type = JsonSerializer.Deserialize("\"content_block_stop\""); } + public RawContentBlockStopEvent(RawContentBlockStopEvent rawContentBlockStopEvent) + : base(rawContentBlockStopEvent) { } + public RawContentBlockStopEvent(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -88,6 +61,7 @@ public RawContentBlockStopEvent(IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static RawContentBlockStopEvent FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -105,6 +79,7 @@ public RawContentBlockStopEvent(long index) class RawContentBlockStopEventFromRaw : IFromRaw { + /// public RawContentBlockStopEvent FromRawUnchecked( IReadOnlyDictionary rawData ) => RawContentBlockStopEvent.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/RawMessageDeltaEvent.cs b/src/Anthropic/Models/Messages/RawMessageDeltaEvent.cs index 416f00c6..fbad9bcd 100644 --- a/src/Anthropic/Models/Messages/RawMessageDeltaEvent.cs +++ b/src/Anthropic/Models/Messages/RawMessageDeltaEvent.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,48 +13,14 @@ public sealed record class RawMessageDeltaEvent : ModelBase { public required Delta Delta { - get - { - if (!this._rawData.TryGetValue("delta", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'delta' cannot be null", - new ArgumentOutOfRangeException("delta", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'delta' cannot be null", - new ArgumentNullException("delta") - ); - } - init - { - this._rawData["delta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "delta"); } + init { ModelBase.Set(this._rawData, "delta", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -77,32 +42,11 @@ public JsonElement Type /// public required MessageDeltaUsage Usage { - get - { - if (!this._rawData.TryGetValue("usage", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'usage' cannot be null", - new ArgumentOutOfRangeException("usage", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'usage' cannot be null", - new ArgumentNullException("usage") - ); - } - init - { - this._rawData["usage"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "usage"); } + init { ModelBase.Set(this._rawData, "usage", value); } } + /// public override void Validate() { this.Delta.Validate(); @@ -123,6 +67,9 @@ public RawMessageDeltaEvent() this.Type = JsonSerializer.Deserialize("\"message_delta\""); } + public RawMessageDeltaEvent(RawMessageDeltaEvent rawMessageDeltaEvent) + : base(rawMessageDeltaEvent) { } + public RawMessageDeltaEvent(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -138,6 +85,7 @@ public RawMessageDeltaEvent(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static RawMessageDeltaEvent FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -148,6 +96,7 @@ IReadOnlyDictionary rawData class RawMessageDeltaEventFromRaw : IFromRaw { + /// public RawMessageDeltaEvent FromRawUnchecked( IReadOnlyDictionary rawData ) => RawMessageDeltaEvent.FromRawUnchecked(rawData); @@ -160,41 +109,21 @@ public required ApiEnum? StopReason { get { - if (!this._rawData.TryGetValue("stop_reason", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["stop_reason"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawData, + "stop_reason" ); } + init { ModelBase.Set(this._rawData, "stop_reason", value); } } public required string? StopSequence { - get - { - if (!this._rawData.TryGetValue("stop_sequence", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["stop_sequence"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "stop_sequence"); } + init { ModelBase.Set(this._rawData, "stop_sequence", value); } } + /// public override void Validate() { this.StopReason?.Validate(); @@ -203,6 +132,9 @@ public override void Validate() public Delta() { } + public Delta(Delta delta) + : base(delta) { } + public Delta(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -216,6 +148,7 @@ public Delta(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static Delta FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -224,6 +157,7 @@ public static Delta FromRawUnchecked(IReadOnlyDictionary ra class DeltaFromRaw : IFromRaw { + /// public Delta FromRawUnchecked(IReadOnlyDictionary rawData) => Delta.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/RawMessageStartEvent.cs b/src/Anthropic/Models/Messages/RawMessageStartEvent.cs index f4ae2fb5..7abcb808 100644 --- a/src/Anthropic/Models/Messages/RawMessageStartEvent.cs +++ b/src/Anthropic/Models/Messages/RawMessageStartEvent.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class RawMessageStartEvent : ModelBase { public required Message Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Message.Validate(); @@ -77,6 +43,9 @@ public RawMessageStartEvent() this.Type = JsonSerializer.Deserialize("\"message_start\""); } + public RawMessageStartEvent(RawMessageStartEvent rawMessageStartEvent) + : base(rawMessageStartEvent) { } + public RawMessageStartEvent(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public RawMessageStartEvent(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static RawMessageStartEvent FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public RawMessageStartEvent(Message message) class RawMessageStartEventFromRaw : IFromRaw { + /// public RawMessageStartEvent FromRawUnchecked( IReadOnlyDictionary rawData ) => RawMessageStartEvent.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/RawMessageStopEvent.cs b/src/Anthropic/Models/Messages/RawMessageStopEvent.cs index 628f5014..9bbc6b16 100644 --- a/src/Anthropic/Models/Messages/RawMessageStopEvent.cs +++ b/src/Anthropic/Models/Messages/RawMessageStopEvent.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,25 +13,11 @@ public sealed record class RawMessageStopEvent : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { if ( @@ -51,6 +36,9 @@ public RawMessageStopEvent() this.Type = JsonSerializer.Deserialize("\"message_stop\""); } + public RawMessageStopEvent(RawMessageStopEvent rawMessageStopEvent) + : base(rawMessageStopEvent) { } + public RawMessageStopEvent(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -66,6 +54,7 @@ public RawMessageStopEvent(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static RawMessageStopEvent FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -76,6 +65,7 @@ IReadOnlyDictionary rawData class RawMessageStopEventFromRaw : IFromRaw { + /// public RawMessageStopEvent FromRawUnchecked(IReadOnlyDictionary rawData) => RawMessageStopEvent.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/RawMessageStreamEvent.cs b/src/Anthropic/Models/Messages/RawMessageStreamEvent.cs index b1771a04..fd819260 100644 --- a/src/Anthropic/Models/Messages/RawMessageStreamEvent.cs +++ b/src/Anthropic/Models/Messages/RawMessageStreamEvent.cs @@ -89,42 +89,156 @@ public RawMessageStreamEvent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickStart(out var value)) { + /// // `value` is of type `RawMessageStartEvent` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickStart([NotNullWhen(true)] out RawMessageStartEvent? value) { value = this.Value as RawMessageStartEvent; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickDelta(out var value)) { + /// // `value` is of type `RawMessageDeltaEvent` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickDelta([NotNullWhen(true)] out RawMessageDeltaEvent? value) { value = this.Value as RawMessageDeltaEvent; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickStop(out var value)) { + /// // `value` is of type `RawMessageStopEvent` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickStop([NotNullWhen(true)] out RawMessageStopEvent? value) { value = this.Value as RawMessageStopEvent; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickContentBlockStart(out var value)) { + /// // `value` is of type `RawContentBlockStartEvent` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickContentBlockStart([NotNullWhen(true)] out RawContentBlockStartEvent? value) { value = this.Value as RawContentBlockStartEvent; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickContentBlockDelta(out var value)) { + /// // `value` is of type `RawContentBlockDeltaEvent` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickContentBlockDelta([NotNullWhen(true)] out RawContentBlockDeltaEvent? value) { value = this.Value as RawContentBlockDeltaEvent; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickContentBlockStop(out var value)) { + /// // `value` is of type `RawContentBlockStopEvent` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickContentBlockStop([NotNullWhen(true)] out RawContentBlockStopEvent? value) { value = this.Value as RawContentBlockStopEvent; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (RawMessageStartEvent value) => {...}, + /// (RawMessageDeltaEvent value) => {...}, + /// (RawMessageStopEvent value) => {...}, + /// (RawContentBlockStartEvent value) => {...}, + /// (RawContentBlockDeltaEvent value) => {...}, + /// (RawContentBlockStopEvent value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action start, System::Action delta, @@ -161,6 +275,31 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (RawMessageStartEvent value) => {...}, + /// (RawMessageDeltaEvent value) => {...}, + /// (RawMessageStopEvent value) => {...}, + /// (RawContentBlockStartEvent value) => {...}, + /// (RawContentBlockDeltaEvent value) => {...}, + /// (RawContentBlockStopEvent value) => {...} + /// ); + /// + /// + /// public T Match( System::Func start, System::Func delta, @@ -199,6 +338,16 @@ public static implicit operator RawMessageStreamEvent(RawContentBlockDeltaEvent public static implicit operator RawMessageStreamEvent(RawContentBlockStopEvent value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -207,6 +356,24 @@ public void Validate() "Data did not match any variant of RawMessageStreamEvent" ); } + this.Switch( + (start) => start.Validate(), + (delta) => delta.Validate(), + (stop) => stop.Validate(), + (contentBlockStart) => contentBlockStart.Validate(), + (contentBlockDelta) => contentBlockDelta.Validate(), + (contentBlockStop) => contentBlockStop.Validate() + ); + } + + public virtual bool Equals(RawMessageStreamEvent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/RedactedThinkingBlock.cs b/src/Anthropic/Models/Messages/RedactedThinkingBlock.cs index 592c9167..2c661eb0 100644 --- a/src/Anthropic/Models/Messages/RedactedThinkingBlock.cs +++ b/src/Anthropic/Models/Messages/RedactedThinkingBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class RedactedThinkingBlock : ModelBase { public required string Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Data; @@ -77,6 +43,9 @@ public RedactedThinkingBlock() this.Type = JsonSerializer.Deserialize("\"redacted_thinking\""); } + public RedactedThinkingBlock(RedactedThinkingBlock redactedThinkingBlock) + : base(redactedThinkingBlock) { } + public RedactedThinkingBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public RedactedThinkingBlock(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static RedactedThinkingBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -109,6 +79,7 @@ public RedactedThinkingBlock(string data) class RedactedThinkingBlockFromRaw : IFromRaw { + /// public RedactedThinkingBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => RedactedThinkingBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/RedactedThinkingBlockParam.cs b/src/Anthropic/Models/Messages/RedactedThinkingBlockParam.cs index db5134f0..71346209 100644 --- a/src/Anthropic/Models/Messages/RedactedThinkingBlockParam.cs +++ b/src/Anthropic/Models/Messages/RedactedThinkingBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,50 +15,17 @@ public sealed record class RedactedThinkingBlockParam : ModelBase { public required string Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Data; @@ -79,6 +45,9 @@ public RedactedThinkingBlockParam() this.Type = JsonSerializer.Deserialize("\"redacted_thinking\""); } + public RedactedThinkingBlockParam(RedactedThinkingBlockParam redactedThinkingBlockParam) + : base(redactedThinkingBlockParam) { } + public RedactedThinkingBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -94,6 +63,7 @@ public RedactedThinkingBlockParam(IReadOnlyDictionary rawDa } #pragma warning restore CS8618 + /// public static RedactedThinkingBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -111,6 +81,7 @@ public RedactedThinkingBlockParam(string data) class RedactedThinkingBlockParamFromRaw : IFromRaw { + /// public RedactedThinkingBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => RedactedThinkingBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/SearchResultBlockParam.cs b/src/Anthropic/Models/Messages/SearchResultBlockParam.cs index 92599141..6bd15cc4 100644 --- a/src/Anthropic/Models/Messages/SearchResultBlockParam.cs +++ b/src/Anthropic/Models/Messages/SearchResultBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,101 +13,26 @@ public sealed record class SearchResultBlockParam : ModelBase { public required IReadOnlyList Content { - get - { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "content"); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string Source { - get - { - if (!this._rawData.TryGetValue("source", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentOutOfRangeException("source", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'source' cannot be null", - new ArgumentNullException("source") - ); - } - init - { - this._rawData["source"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "source"); } + init { ModelBase.Set(this._rawData, "source", value); } } public required string Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'title' cannot be null", - new ArgumentOutOfRangeException("title", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'title' cannot be null", - new ArgumentNullException("title") - ); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -118,35 +42,14 @@ public CacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "cache_control"); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } public CitationsConfigParam? Citations { - get - { - if (!this._rawData.TryGetValue("citations", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "citations"); } init { if (value == null) @@ -154,13 +57,11 @@ public CitationsConfigParam? Citations return; } - this._rawData["citations"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "citations", value); } } + /// public override void Validate() { foreach (var item in this.Content) @@ -187,6 +88,9 @@ public SearchResultBlockParam() this.Type = JsonSerializer.Deserialize("\"search_result\""); } + public SearchResultBlockParam(SearchResultBlockParam searchResultBlockParam) + : base(searchResultBlockParam) { } + public SearchResultBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -202,6 +106,7 @@ public SearchResultBlockParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static SearchResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -212,6 +117,7 @@ IReadOnlyDictionary rawData class SearchResultBlockParamFromRaw : IFromRaw { + /// public SearchResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => SearchResultBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/ServerToolUsage.cs b/src/Anthropic/Models/Messages/ServerToolUsage.cs index eeeafd1d..d77bd8b9 100644 --- a/src/Anthropic/Models/Messages/ServerToolUsage.cs +++ b/src/Anthropic/Models/Messages/ServerToolUsage.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Messages; @@ -17,28 +15,11 @@ public sealed record class ServerToolUsage : ModelBase /// public required long WebSearchRequests { - get - { - if (!this._rawData.TryGetValue("web_search_requests", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'web_search_requests' cannot be null", - new ArgumentOutOfRangeException( - "web_search_requests", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["web_search_requests"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "web_search_requests"); } + init { ModelBase.Set(this._rawData, "web_search_requests", value); } } + /// public override void Validate() { _ = this.WebSearchRequests; @@ -46,6 +27,9 @@ public override void Validate() public ServerToolUsage() { } + public ServerToolUsage(ServerToolUsage serverToolUsage) + : base(serverToolUsage) { } + public ServerToolUsage(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -59,6 +43,7 @@ public ServerToolUsage(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ServerToolUsage FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -74,6 +59,7 @@ public ServerToolUsage(long webSearchRequests) class ServerToolUsageFromRaw : IFromRaw { + /// public ServerToolUsage FromRawUnchecked(IReadOnlyDictionary rawData) => ServerToolUsage.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/ServerToolUseBlock.cs b/src/Anthropic/Models/Messages/ServerToolUseBlock.cs index f62acf7c..07770cc1 100644 --- a/src/Anthropic/Models/Messages/ServerToolUseBlock.cs +++ b/src/Anthropic/Models/Messages/ServerToolUseBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,99 +13,35 @@ public sealed record class ServerToolUseBlock : ModelBase { public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } public required IReadOnlyDictionary Input { get { - if (!this._rawData.TryGetValue("input", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input' cannot be null", - new ArgumentOutOfRangeException("input", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'input' cannot be null", - new ArgumentNullException("input") - ); - } - init - { - this._rawData["input"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "input" ); } + init { ModelBase.Set(this._rawData, "input", value); } } public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ID; @@ -137,6 +72,9 @@ public ServerToolUseBlock() this.Type = JsonSerializer.Deserialize("\"server_tool_use\""); } + public ServerToolUseBlock(ServerToolUseBlock serverToolUseBlock) + : base(serverToolUseBlock) { } + public ServerToolUseBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -153,6 +91,7 @@ public ServerToolUseBlock(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ServerToolUseBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -163,6 +102,7 @@ IReadOnlyDictionary rawData class ServerToolUseBlockFromRaw : IFromRaw { + /// public ServerToolUseBlock FromRawUnchecked(IReadOnlyDictionary rawData) => ServerToolUseBlock.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/ServerToolUseBlockParam.cs b/src/Anthropic/Models/Messages/ServerToolUseBlockParam.cs index e2050f09..4a27e131 100644 --- a/src/Anthropic/Models/Messages/ServerToolUseBlockParam.cs +++ b/src/Anthropic/Models/Messages/ServerToolUseBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,97 +13,32 @@ public sealed record class ServerToolUseBlockParam : ModelBase { public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } public required IReadOnlyDictionary Input { get { - if (!this._rawData.TryGetValue("input", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input' cannot be null", - new ArgumentOutOfRangeException("input", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'input' cannot be null", - new ArgumentNullException("input") - ); - } - init - { - this._rawData["input"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "input" ); } + init { ModelBase.Set(this._rawData, "input", value); } } public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -114,23 +48,12 @@ public CacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "cache_control"); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { _ = this.ID; @@ -162,6 +85,9 @@ public ServerToolUseBlockParam() this.Type = JsonSerializer.Deserialize("\"server_tool_use\""); } + public ServerToolUseBlockParam(ServerToolUseBlockParam serverToolUseBlockParam) + : base(serverToolUseBlockParam) { } + public ServerToolUseBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -178,6 +104,7 @@ public ServerToolUseBlockParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ServerToolUseBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -188,6 +115,7 @@ IReadOnlyDictionary rawData class ServerToolUseBlockParamFromRaw : IFromRaw { + /// public ServerToolUseBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => ServerToolUseBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/SignatureDelta.cs b/src/Anthropic/Models/Messages/SignatureDelta.cs index 2473efbe..d93860fe 100644 --- a/src/Anthropic/Models/Messages/SignatureDelta.cs +++ b/src/Anthropic/Models/Messages/SignatureDelta.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class SignatureDelta : ModelBase { public required string Signature { - get - { - if (!this._rawData.TryGetValue("signature", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'signature' cannot be null", - new ArgumentOutOfRangeException("signature", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'signature' cannot be null", - new ArgumentNullException("signature") - ); - } - init - { - this._rawData["signature"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "signature"); } + init { ModelBase.Set(this._rawData, "signature", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Signature; @@ -77,6 +43,9 @@ public SignatureDelta() this.Type = JsonSerializer.Deserialize("\"signature_delta\""); } + public SignatureDelta(SignatureDelta signatureDelta) + : base(signatureDelta) { } + public SignatureDelta(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public SignatureDelta(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static SignatureDelta FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -107,6 +77,7 @@ public SignatureDelta(string signature) class SignatureDeltaFromRaw : IFromRaw { + /// public SignatureDelta FromRawUnchecked(IReadOnlyDictionary rawData) => SignatureDelta.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/TextBlock.cs b/src/Anthropic/Models/Messages/TextBlock.cs index da5ac0f8..e616c13b 100644 --- a/src/Anthropic/Models/Messages/TextBlock.cs +++ b/src/Anthropic/Models/Messages/TextBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -21,71 +20,23 @@ public sealed record class TextBlock : ModelBase /// public required IReadOnlyList? Citations { - get - { - if (!this._rawData.TryGetValue("citations", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["citations"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "citations"); } + init { ModelBase.Set(this._rawData, "citations", value); } } public required string Text { - get - { - if (!this._rawData.TryGetValue("text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'text' cannot be null", - new ArgumentOutOfRangeException("text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'text' cannot be null", - new ArgumentNullException("text") - ); - } - init - { - this._rawData["text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "text"); } + init { ModelBase.Set(this._rawData, "text", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { foreach (var item in this.Citations ?? []) @@ -104,6 +55,9 @@ public TextBlock() this.Type = JsonSerializer.Deserialize("\"text\""); } + public TextBlock(TextBlock textBlock) + : base(textBlock) { } + public TextBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -119,6 +73,7 @@ public TextBlock(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static TextBlock FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -127,6 +82,7 @@ public static TextBlock FromRawUnchecked(IReadOnlyDictionary { + /// public TextBlock FromRawUnchecked(IReadOnlyDictionary rawData) => TextBlock.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/TextBlockParam.cs b/src/Anthropic/Models/Messages/TextBlockParam.cs index 86d9ac5a..b5b52827 100644 --- a/src/Anthropic/Models/Messages/TextBlockParam.cs +++ b/src/Anthropic/Models/Messages/TextBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,48 +13,14 @@ public sealed record class TextBlockParam : ModelBase { public required string Text { - get - { - if (!this._rawData.TryGetValue("text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'text' cannot be null", - new ArgumentOutOfRangeException("text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'text' cannot be null", - new ArgumentNullException("text") - ); - } - init - { - this._rawData["text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "text"); } + init { ModelBase.Set(this._rawData, "text", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -65,44 +30,21 @@ public CacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "cache_control"); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } public IReadOnlyList? Citations { get { - if (!this._rawData.TryGetValue("citations", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["citations"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass>(this.RawData, "citations"); } + init { ModelBase.Set(this._rawData, "citations", value); } } + /// public override void Validate() { _ = this.Text; @@ -122,6 +64,9 @@ public TextBlockParam() this.Type = JsonSerializer.Deserialize("\"text\""); } + public TextBlockParam(TextBlockParam textBlockParam) + : base(textBlockParam) { } + public TextBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -137,6 +82,7 @@ public TextBlockParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static TextBlockParam FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -152,6 +98,7 @@ public TextBlockParam(string text) class TextBlockParamFromRaw : IFromRaw { + /// public TextBlockParam FromRawUnchecked(IReadOnlyDictionary rawData) => TextBlockParam.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/TextCitation.cs b/src/Anthropic/Models/Messages/TextCitation.cs index bbfe8277..6eccd689 100644 --- a/src/Anthropic/Models/Messages/TextCitation.cs +++ b/src/Anthropic/Models/Messages/TextCitation.cs @@ -165,18 +165,63 @@ public TextCitation(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationCharLocation(out var value)) { + /// // `value` is of type `CitationCharLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationCharLocation([NotNullWhen(true)] out CitationCharLocation? value) { value = this.Value as CitationCharLocation; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationPageLocation(out var value)) { + /// // `value` is of type `CitationPageLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationPageLocation([NotNullWhen(true)] out CitationPageLocation? value) { value = this.Value as CitationPageLocation; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationContentBlockLocation(out var value)) { + /// // `value` is of type `CitationContentBlockLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationContentBlockLocation( [NotNullWhen(true)] out CitationContentBlockLocation? value ) @@ -185,6 +230,21 @@ public bool TryPickCitationContentBlockLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationsWebSearchResultLocation(out var value)) { + /// // `value` is of type `CitationsWebSearchResultLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationsWebSearchResultLocation( [NotNullWhen(true)] out CitationsWebSearchResultLocation? value ) @@ -193,6 +253,21 @@ public bool TryPickCitationsWebSearchResultLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationsSearchResultLocation(out var value)) { + /// // `value` is of type `CitationsSearchResultLocation` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationsSearchResultLocation( [NotNullWhen(true)] out CitationsSearchResultLocation? value ) @@ -201,6 +276,29 @@ public bool TryPickCitationsSearchResultLocation( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (CitationCharLocation value) => {...}, + /// (CitationPageLocation value) => {...}, + /// (CitationContentBlockLocation value) => {...}, + /// (CitationsWebSearchResultLocation value) => {...}, + /// (CitationsSearchResultLocation value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action citationCharLocation, System::Action citationPageLocation, @@ -233,6 +331,30 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (CitationCharLocation value) => {...}, + /// (CitationPageLocation value) => {...}, + /// (CitationContentBlockLocation value) => {...}, + /// (CitationsWebSearchResultLocation value) => {...}, + /// (CitationsSearchResultLocation value) => {...} + /// ); + /// + /// + /// public T Match( System::Func citationCharLocation, System::Func citationPageLocation, @@ -265,6 +387,16 @@ public static implicit operator TextCitation(CitationsWebSearchResultLocation va public static implicit operator TextCitation(CitationsSearchResultLocation value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -273,6 +405,23 @@ public void Validate() "Data did not match any variant of TextCitation" ); } + this.Switch( + (citationCharLocation) => citationCharLocation.Validate(), + (citationPageLocation) => citationPageLocation.Validate(), + (citationContentBlockLocation) => citationContentBlockLocation.Validate(), + (citationsWebSearchResultLocation) => citationsWebSearchResultLocation.Validate(), + (citationsSearchResultLocation) => citationsSearchResultLocation.Validate() + ); + } + + public virtual bool Equals(TextCitation? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/TextCitationParam.cs b/src/Anthropic/Models/Messages/TextCitationParam.cs index 33a2a9b2..78ada98a 100644 --- a/src/Anthropic/Models/Messages/TextCitationParam.cs +++ b/src/Anthropic/Models/Messages/TextCitationParam.cs @@ -151,6 +151,21 @@ public TextCitationParam(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationCharLocation(out var value)) { + /// // `value` is of type `CitationCharLocationParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationCharLocation( [NotNullWhen(true)] out CitationCharLocationParam? value ) @@ -159,6 +174,21 @@ public bool TryPickCitationCharLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationPageLocation(out var value)) { + /// // `value` is of type `CitationPageLocationParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationPageLocation( [NotNullWhen(true)] out CitationPageLocationParam? value ) @@ -167,6 +197,21 @@ public bool TryPickCitationPageLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationContentBlockLocation(out var value)) { + /// // `value` is of type `CitationContentBlockLocationParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationContentBlockLocation( [NotNullWhen(true)] out CitationContentBlockLocationParam? value ) @@ -175,6 +220,21 @@ public bool TryPickCitationContentBlockLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationWebSearchResultLocation(out var value)) { + /// // `value` is of type `CitationWebSearchResultLocationParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationWebSearchResultLocation( [NotNullWhen(true)] out CitationWebSearchResultLocationParam? value ) @@ -183,6 +243,21 @@ public bool TryPickCitationWebSearchResultLocation( return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickCitationSearchResultLocation(out var value)) { + /// // `value` is of type `CitationSearchResultLocationParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickCitationSearchResultLocation( [NotNullWhen(true)] out CitationSearchResultLocationParam? value ) @@ -191,6 +266,29 @@ public bool TryPickCitationSearchResultLocation( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (CitationCharLocationParam value) => {...}, + /// (CitationPageLocationParam value) => {...}, + /// (CitationContentBlockLocationParam value) => {...}, + /// (CitationWebSearchResultLocationParam value) => {...}, + /// (CitationSearchResultLocationParam value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action citationCharLocation, System::Action citationPageLocation, @@ -223,6 +321,30 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (CitationCharLocationParam value) => {...}, + /// (CitationPageLocationParam value) => {...}, + /// (CitationContentBlockLocationParam value) => {...}, + /// (CitationWebSearchResultLocationParam value) => {...}, + /// (CitationSearchResultLocationParam value) => {...} + /// ); + /// + /// + /// public T Match( System::Func citationCharLocation, System::Func citationPageLocation, @@ -259,6 +381,16 @@ public static implicit operator TextCitationParam(CitationWebSearchResultLocatio public static implicit operator TextCitationParam(CitationSearchResultLocationParam value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -267,6 +399,23 @@ public void Validate() "Data did not match any variant of TextCitationParam" ); } + this.Switch( + (citationCharLocation) => citationCharLocation.Validate(), + (citationPageLocation) => citationPageLocation.Validate(), + (citationContentBlockLocation) => citationContentBlockLocation.Validate(), + (citationWebSearchResultLocation) => citationWebSearchResultLocation.Validate(), + (citationSearchResultLocation) => citationSearchResultLocation.Validate() + ); + } + + public virtual bool Equals(TextCitationParam? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/TextDelta.cs b/src/Anthropic/Models/Messages/TextDelta.cs index 4f92a305..e24fdd04 100644 --- a/src/Anthropic/Models/Messages/TextDelta.cs +++ b/src/Anthropic/Models/Messages/TextDelta.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class TextDelta : ModelBase { public required string Text { - get - { - if (!this._rawData.TryGetValue("text", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'text' cannot be null", - new ArgumentOutOfRangeException("text", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'text' cannot be null", - new ArgumentNullException("text") - ); - } - init - { - this._rawData["text"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "text"); } + init { ModelBase.Set(this._rawData, "text", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Text; @@ -77,6 +43,9 @@ public TextDelta() this.Type = JsonSerializer.Deserialize("\"text_delta\""); } + public TextDelta(TextDelta textDelta) + : base(textDelta) { } + public TextDelta(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public TextDelta(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static TextDelta FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -107,6 +77,7 @@ public TextDelta(string text) class TextDeltaFromRaw : IFromRaw { + /// public TextDelta FromRawUnchecked(IReadOnlyDictionary rawData) => TextDelta.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/ThinkingBlock.cs b/src/Anthropic/Models/Messages/ThinkingBlock.cs index 8de4bb85..c575bfc0 100644 --- a/src/Anthropic/Models/Messages/ThinkingBlock.cs +++ b/src/Anthropic/Models/Messages/ThinkingBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,75 +13,23 @@ public sealed record class ThinkingBlock : ModelBase { public required string Signature { - get - { - if (!this._rawData.TryGetValue("signature", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'signature' cannot be null", - new ArgumentOutOfRangeException("signature", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'signature' cannot be null", - new ArgumentNullException("signature") - ); - } - init - { - this._rawData["signature"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "signature"); } + init { ModelBase.Set(this._rawData, "signature", value); } } public required string Thinking { - get - { - if (!this._rawData.TryGetValue("thinking", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'thinking' cannot be null", - new ArgumentOutOfRangeException("thinking", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'thinking' cannot be null", - new ArgumentNullException("thinking") - ); - } - init - { - this._rawData["thinking"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "thinking"); } + init { ModelBase.Set(this._rawData, "thinking", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Signature; @@ -103,6 +50,9 @@ public ThinkingBlock() this.Type = JsonSerializer.Deserialize("\"thinking\""); } + public ThinkingBlock(ThinkingBlock thinkingBlock) + : base(thinkingBlock) { } + public ThinkingBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -118,6 +68,7 @@ public ThinkingBlock(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ThinkingBlock FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -126,6 +77,7 @@ public static ThinkingBlock FromRawUnchecked(IReadOnlyDictionary { + /// public ThinkingBlock FromRawUnchecked(IReadOnlyDictionary rawData) => ThinkingBlock.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/ThinkingBlockParam.cs b/src/Anthropic/Models/Messages/ThinkingBlockParam.cs index 805e3093..81dde4d0 100644 --- a/src/Anthropic/Models/Messages/ThinkingBlockParam.cs +++ b/src/Anthropic/Models/Messages/ThinkingBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,75 +13,23 @@ public sealed record class ThinkingBlockParam : ModelBase { public required string Signature { - get - { - if (!this._rawData.TryGetValue("signature", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'signature' cannot be null", - new ArgumentOutOfRangeException("signature", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'signature' cannot be null", - new ArgumentNullException("signature") - ); - } - init - { - this._rawData["signature"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "signature"); } + init { ModelBase.Set(this._rawData, "signature", value); } } public required string Thinking { - get - { - if (!this._rawData.TryGetValue("thinking", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'thinking' cannot be null", - new ArgumentOutOfRangeException("thinking", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'thinking' cannot be null", - new ArgumentNullException("thinking") - ); - } - init - { - this._rawData["thinking"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "thinking"); } + init { ModelBase.Set(this._rawData, "thinking", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Signature; @@ -103,6 +50,9 @@ public ThinkingBlockParam() this.Type = JsonSerializer.Deserialize("\"thinking\""); } + public ThinkingBlockParam(ThinkingBlockParam thinkingBlockParam) + : base(thinkingBlockParam) { } + public ThinkingBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -118,6 +68,7 @@ public ThinkingBlockParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ThinkingBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -128,6 +79,7 @@ IReadOnlyDictionary rawData class ThinkingBlockParamFromRaw : IFromRaw { + /// public ThinkingBlockParam FromRawUnchecked(IReadOnlyDictionary rawData) => ThinkingBlockParam.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/ThinkingConfigDisabled.cs b/src/Anthropic/Models/Messages/ThinkingConfigDisabled.cs index feb6135f..0a662d56 100644 --- a/src/Anthropic/Models/Messages/ThinkingConfigDisabled.cs +++ b/src/Anthropic/Models/Messages/ThinkingConfigDisabled.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,25 +13,11 @@ public sealed record class ThinkingConfigDisabled : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { if ( @@ -51,6 +36,9 @@ public ThinkingConfigDisabled() this.Type = JsonSerializer.Deserialize("\"disabled\""); } + public ThinkingConfigDisabled(ThinkingConfigDisabled thinkingConfigDisabled) + : base(thinkingConfigDisabled) { } + public ThinkingConfigDisabled(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -66,6 +54,7 @@ public ThinkingConfigDisabled(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ThinkingConfigDisabled FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -76,6 +65,7 @@ IReadOnlyDictionary rawData class ThinkingConfigDisabledFromRaw : IFromRaw { + /// public ThinkingConfigDisabled FromRawUnchecked( IReadOnlyDictionary rawData ) => ThinkingConfigDisabled.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/ThinkingConfigEnabled.cs b/src/Anthropic/Models/Messages/ThinkingConfigEnabled.cs index 6a082342..c5648de1 100644 --- a/src/Anthropic/Models/Messages/ThinkingConfigEnabled.cs +++ b/src/Anthropic/Models/Messages/ThinkingConfigEnabled.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -24,46 +23,17 @@ public sealed record class ThinkingConfigEnabled : ModelBase /// public required long BudgetTokens { - get - { - if (!this._rawData.TryGetValue("budget_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'budget_tokens' cannot be null", - new ArgumentOutOfRangeException("budget_tokens", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["budget_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "budget_tokens"); } + init { ModelBase.Set(this._rawData, "budget_tokens", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.BudgetTokens; @@ -83,6 +53,9 @@ public ThinkingConfigEnabled() this.Type = JsonSerializer.Deserialize("\"enabled\""); } + public ThinkingConfigEnabled(ThinkingConfigEnabled thinkingConfigEnabled) + : base(thinkingConfigEnabled) { } + public ThinkingConfigEnabled(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -98,6 +71,7 @@ public ThinkingConfigEnabled(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ThinkingConfigEnabled FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -115,6 +89,7 @@ public ThinkingConfigEnabled(long budgetTokens) class ThinkingConfigEnabledFromRaw : IFromRaw { + /// public ThinkingConfigEnabled FromRawUnchecked( IReadOnlyDictionary rawData ) => ThinkingConfigEnabled.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/ThinkingConfigParam.cs b/src/Anthropic/Models/Messages/ThinkingConfigParam.cs index 7b750473..255be41e 100644 --- a/src/Anthropic/Models/Messages/ThinkingConfigParam.cs +++ b/src/Anthropic/Models/Messages/ThinkingConfigParam.cs @@ -50,18 +50,68 @@ public ThinkingConfigParam(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickEnabled(out var value)) { + /// // `value` is of type `ThinkingConfigEnabled` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickEnabled([NotNullWhen(true)] out ThinkingConfigEnabled? value) { value = this.Value as ThinkingConfigEnabled; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickDisabled(out var value)) { + /// // `value` is of type `ThinkingConfigDisabled` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickDisabled([NotNullWhen(true)] out ThinkingConfigDisabled? value) { value = this.Value as ThinkingConfigDisabled; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (ThinkingConfigEnabled value) => {...}, + /// (ThinkingConfigDisabled value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action enabled, System::Action disabled @@ -82,6 +132,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (ThinkingConfigEnabled value) => {...}, + /// (ThinkingConfigDisabled value) => {...} + /// ); + /// + /// + /// public T Match( System::Func enabled, System::Func disabled @@ -101,6 +172,16 @@ public T Match( public static implicit operator ThinkingConfigParam(ThinkingConfigDisabled value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -109,6 +190,17 @@ public void Validate() "Data did not match any variant of ThinkingConfigParam" ); } + this.Switch((enabled) => enabled.Validate(), (disabled) => disabled.Validate()); + } + + public virtual bool Equals(ThinkingConfigParam? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/ThinkingDelta.cs b/src/Anthropic/Models/Messages/ThinkingDelta.cs index 103077fd..80ad7828 100644 --- a/src/Anthropic/Models/Messages/ThinkingDelta.cs +++ b/src/Anthropic/Models/Messages/ThinkingDelta.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class ThinkingDelta : ModelBase { public required string Thinking { - get - { - if (!this._rawData.TryGetValue("thinking", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'thinking' cannot be null", - new ArgumentOutOfRangeException("thinking", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'thinking' cannot be null", - new ArgumentNullException("thinking") - ); - } - init - { - this._rawData["thinking"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "thinking"); } + init { ModelBase.Set(this._rawData, "thinking", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Thinking; @@ -77,6 +43,9 @@ public ThinkingDelta() this.Type = JsonSerializer.Deserialize("\"thinking_delta\""); } + public ThinkingDelta(ThinkingDelta thinkingDelta) + : base(thinkingDelta) { } + public ThinkingDelta(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public ThinkingDelta(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ThinkingDelta FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -107,6 +77,7 @@ public ThinkingDelta(string thinking) class ThinkingDeltaFromRaw : IFromRaw { + /// public ThinkingDelta FromRawUnchecked(IReadOnlyDictionary rawData) => ThinkingDelta.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/Tool.cs b/src/Anthropic/Models/Messages/Tool.cs index 7b2ea8c8..759c0b65 100644 --- a/src/Anthropic/Models/Messages/Tool.cs +++ b/src/Anthropic/Models/Messages/Tool.cs @@ -20,30 +20,8 @@ public sealed record class Tool : ModelBase /// public required InputSchema InputSchema { - get - { - if (!this._rawData.TryGetValue("input_schema", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input_schema' cannot be null", - new System::ArgumentOutOfRangeException( - "input_schema", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'input_schema' cannot be null", - new System::ArgumentNullException("input_schema") - ); - } - init - { - this._rawData["input_schema"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "input_schema"); } + init { ModelBase.Set(this._rawData, "input_schema", value); } } /// @@ -53,27 +31,8 @@ public required InputSchema InputSchema /// public required string Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'name' cannot be null", - new System::ArgumentNullException("name") - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } /// @@ -83,21 +42,9 @@ public CacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "cache_control"); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -110,13 +57,7 @@ public CacheControlEphemeral? CacheControl /// public string? Description { - get - { - if (!this._rawData.TryGetValue("description", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawData, "description"); } init { if (value == null) @@ -124,10 +65,7 @@ public string? Description return; } - this._rawData["description"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "description", value); } } @@ -135,23 +73,14 @@ public string? Description { get { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass< + ApiEnum + >(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.InputSchema.Validate(); @@ -163,6 +92,9 @@ public override void Validate() public Tool() { } + public Tool(Tool tool) + : base(tool) { } + public Tool(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -176,6 +108,7 @@ public Tool(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static Tool FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -184,6 +117,7 @@ public static Tool FromRawUnchecked(IReadOnlyDictionary raw class ToolFromRaw : IFromRaw { + /// public Tool FromRawUnchecked(IReadOnlyDictionary rawData) => Tool.FromRawUnchecked(rawData); } @@ -199,64 +133,29 @@ public sealed record class InputSchema : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public IReadOnlyDictionary? Properties { get { - if (!this._rawData.TryGetValue("properties", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["properties"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawData, + "properties" ); } + init { ModelBase.Set(this._rawData, "properties", value); } } public IReadOnlyList? Required { - get - { - if (!this._rawData.TryGetValue("required", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["required"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "required"); } + init { ModelBase.Set(this._rawData, "required", value); } } + /// public override void Validate() { if ( @@ -277,6 +176,9 @@ public InputSchema() this.Type = JsonSerializer.Deserialize("\"object\""); } + public InputSchema(InputSchema inputSchema) + : base(inputSchema) { } + public InputSchema(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -292,6 +194,7 @@ public InputSchema(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static InputSchema FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -300,6 +203,7 @@ public static InputSchema FromRawUnchecked(IReadOnlyDictionary { + /// public InputSchema FromRawUnchecked(IReadOnlyDictionary rawData) => InputSchema.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/ToolBash20250124.cs b/src/Anthropic/Models/Messages/ToolBash20250124.cs index 386c9f12..dbaf3f03 100644 --- a/src/Anthropic/Models/Messages/ToolBash20250124.cs +++ b/src/Anthropic/Models/Messages/ToolBash20250124.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,44 +18,14 @@ public sealed record class ToolBash20250124 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -66,23 +35,12 @@ public CacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "cache_control"); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { if (!JsonElement.DeepEquals(this.Name, JsonSerializer.Deserialize("\"bash\""))) @@ -107,6 +65,9 @@ public ToolBash20250124() this.Type = JsonSerializer.Deserialize("\"bash_20250124\""); } + public ToolBash20250124(ToolBash20250124 toolBash20250124) + : base(toolBash20250124) { } + public ToolBash20250124(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -123,6 +84,7 @@ public ToolBash20250124(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ToolBash20250124 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -133,6 +95,7 @@ IReadOnlyDictionary rawData class ToolBash20250124FromRaw : IFromRaw { + /// public ToolBash20250124 FromRawUnchecked(IReadOnlyDictionary rawData) => ToolBash20250124.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/ToolChoice.cs b/src/Anthropic/Models/Messages/ToolChoice.cs index a375d3bc..a0c192cf 100644 --- a/src/Anthropic/Models/Messages/ToolChoice.cs +++ b/src/Anthropic/Models/Messages/ToolChoice.cs @@ -77,30 +77,112 @@ public ToolChoice(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickAuto(out var value)) { + /// // `value` is of type `ToolChoiceAuto` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickAuto([NotNullWhen(true)] out ToolChoiceAuto? value) { value = this.Value as ToolChoiceAuto; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickAny(out var value)) { + /// // `value` is of type `ToolChoiceAny` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickAny([NotNullWhen(true)] out ToolChoiceAny? value) { value = this.Value as ToolChoiceAny; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTool(out var value)) { + /// // `value` is of type `ToolChoiceTool` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTool([NotNullWhen(true)] out ToolChoiceTool? value) { value = this.Value as ToolChoiceTool; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickNone(out var value)) { + /// // `value` is of type `ToolChoiceNone` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickNone([NotNullWhen(true)] out ToolChoiceNone? value) { value = this.Value as ToolChoiceNone; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (ToolChoiceAuto value) => {...}, + /// (ToolChoiceAny value) => {...}, + /// (ToolChoiceTool value) => {...}, + /// (ToolChoiceNone value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action auto, System::Action any, @@ -129,6 +211,29 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (ToolChoiceAuto value) => {...}, + /// (ToolChoiceAny value) => {...}, + /// (ToolChoiceTool value) => {...}, + /// (ToolChoiceNone value) => {...} + /// ); + /// + /// + /// public T Match( System::Func auto, System::Func any, @@ -156,12 +261,38 @@ public T Match( public static implicit operator ToolChoice(ToolChoiceNone value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of ToolChoice"); } + this.Switch( + (auto) => auto.Validate(), + (any) => any.Validate(), + (tool) => tool.Validate(), + (none) => none.Validate() + ); + } + + public virtual bool Equals(ToolChoice? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/ToolChoiceAny.cs b/src/Anthropic/Models/Messages/ToolChoiceAny.cs index 6ec6a883..9e8db5dd 100644 --- a/src/Anthropic/Models/Messages/ToolChoiceAny.cs +++ b/src/Anthropic/Models/Messages/ToolChoiceAny.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -17,23 +16,8 @@ public sealed record class ToolChoiceAny : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -44,13 +28,7 @@ public JsonElement Type /// public bool? DisableParallelToolUse { - get - { - if (!this._rawData.TryGetValue("disable_parallel_tool_use", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "disable_parallel_tool_use"); } init { if (value == null) @@ -58,13 +36,11 @@ public bool? DisableParallelToolUse return; } - this._rawData["disable_parallel_tool_use"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "disable_parallel_tool_use", value); } } + /// public override void Validate() { if (!JsonElement.DeepEquals(this.Type, JsonSerializer.Deserialize("\"any\""))) @@ -79,6 +55,9 @@ public ToolChoiceAny() this.Type = JsonSerializer.Deserialize("\"any\""); } + public ToolChoiceAny(ToolChoiceAny toolChoiceAny) + : base(toolChoiceAny) { } + public ToolChoiceAny(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -94,6 +73,7 @@ public ToolChoiceAny(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ToolChoiceAny FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -102,6 +82,7 @@ public static ToolChoiceAny FromRawUnchecked(IReadOnlyDictionary { + /// public ToolChoiceAny FromRawUnchecked(IReadOnlyDictionary rawData) => ToolChoiceAny.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/ToolChoiceAuto.cs b/src/Anthropic/Models/Messages/ToolChoiceAuto.cs index e855c753..ea900d81 100644 --- a/src/Anthropic/Models/Messages/ToolChoiceAuto.cs +++ b/src/Anthropic/Models/Messages/ToolChoiceAuto.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -17,23 +16,8 @@ public sealed record class ToolChoiceAuto : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -44,13 +28,7 @@ public JsonElement Type /// public bool? DisableParallelToolUse { - get - { - if (!this._rawData.TryGetValue("disable_parallel_tool_use", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "disable_parallel_tool_use"); } init { if (value == null) @@ -58,13 +36,11 @@ public bool? DisableParallelToolUse return; } - this._rawData["disable_parallel_tool_use"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "disable_parallel_tool_use", value); } } + /// public override void Validate() { if (!JsonElement.DeepEquals(this.Type, JsonSerializer.Deserialize("\"auto\""))) @@ -79,6 +55,9 @@ public ToolChoiceAuto() this.Type = JsonSerializer.Deserialize("\"auto\""); } + public ToolChoiceAuto(ToolChoiceAuto toolChoiceAuto) + : base(toolChoiceAuto) { } + public ToolChoiceAuto(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -94,6 +73,7 @@ public ToolChoiceAuto(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ToolChoiceAuto FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -102,6 +82,7 @@ public static ToolChoiceAuto FromRawUnchecked(IReadOnlyDictionary { + /// public ToolChoiceAuto FromRawUnchecked(IReadOnlyDictionary rawData) => ToolChoiceAuto.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/ToolChoiceNone.cs b/src/Anthropic/Models/Messages/ToolChoiceNone.cs index 50536c65..1bcb5492 100644 --- a/src/Anthropic/Models/Messages/ToolChoiceNone.cs +++ b/src/Anthropic/Models/Messages/ToolChoiceNone.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -17,25 +16,11 @@ public sealed record class ToolChoiceNone : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { if (!JsonElement.DeepEquals(this.Type, JsonSerializer.Deserialize("\"none\""))) @@ -49,6 +34,9 @@ public ToolChoiceNone() this.Type = JsonSerializer.Deserialize("\"none\""); } + public ToolChoiceNone(ToolChoiceNone toolChoiceNone) + : base(toolChoiceNone) { } + public ToolChoiceNone(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -64,6 +52,7 @@ public ToolChoiceNone(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ToolChoiceNone FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -72,6 +61,7 @@ public static ToolChoiceNone FromRawUnchecked(IReadOnlyDictionary { + /// public ToolChoiceNone FromRawUnchecked(IReadOnlyDictionary rawData) => ToolChoiceNone.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/ToolChoiceTool.cs b/src/Anthropic/Models/Messages/ToolChoiceTool.cs index c0eb9b2a..761534cb 100644 --- a/src/Anthropic/Models/Messages/ToolChoiceTool.cs +++ b/src/Anthropic/Models/Messages/ToolChoiceTool.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -20,48 +19,14 @@ public sealed record class ToolChoiceTool : ModelBase /// public required string Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentNullException("name") - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -72,13 +37,7 @@ public JsonElement Type /// public bool? DisableParallelToolUse { - get - { - if (!this._rawData.TryGetValue("disable_parallel_tool_use", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "disable_parallel_tool_use"); } init { if (value == null) @@ -86,13 +45,11 @@ public bool? DisableParallelToolUse return; } - this._rawData["disable_parallel_tool_use"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "disable_parallel_tool_use", value); } } + /// public override void Validate() { _ = this.Name; @@ -108,6 +65,9 @@ public ToolChoiceTool() this.Type = JsonSerializer.Deserialize("\"tool\""); } + public ToolChoiceTool(ToolChoiceTool toolChoiceTool) + : base(toolChoiceTool) { } + public ToolChoiceTool(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -123,6 +83,7 @@ public ToolChoiceTool(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ToolChoiceTool FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -138,6 +99,7 @@ public ToolChoiceTool(string name) class ToolChoiceToolFromRaw : IFromRaw { + /// public ToolChoiceTool FromRawUnchecked(IReadOnlyDictionary rawData) => ToolChoiceTool.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/ToolResultBlockParam.cs b/src/Anthropic/Models/Messages/ToolResultBlockParam.cs index dc207202..3b6b623e 100644 --- a/src/Anthropic/Models/Messages/ToolResultBlockParam.cs +++ b/src/Anthropic/Models/Messages/ToolResultBlockParam.cs @@ -15,51 +15,14 @@ public sealed record class ToolResultBlockParam : ModelBase { public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentOutOfRangeException( - "tool_use_id", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new System::ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -69,34 +32,16 @@ public CacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "cache_control"); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } public ToolResultBlockParamContent? Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "content"); } init { @@ -105,22 +50,13 @@ public ToolResultBlockParamContent? Content return; } - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "content", value); } } public bool? IsError { - get - { - if (!this._rawData.TryGetValue("is_error", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawData, "is_error"); } init { if (value == null) @@ -128,13 +64,11 @@ public bool? IsError return; } - this._rawData["is_error"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawData, "is_error", value); } } + /// public override void Validate() { _ = this.ToolUseID; @@ -157,6 +91,9 @@ public ToolResultBlockParam() this.Type = JsonSerializer.Deserialize("\"tool_result\""); } + public ToolResultBlockParam(ToolResultBlockParam toolResultBlockParam) + : base(toolResultBlockParam) { } + public ToolResultBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -172,6 +109,7 @@ public ToolResultBlockParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -189,6 +127,7 @@ public ToolResultBlockParam(string toolUseID) class ToolResultBlockParamFromRaw : IFromRaw { + /// public ToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => ToolResultBlockParam.FromRawUnchecked(rawData); @@ -223,18 +162,68 @@ public ToolResultBlockParamContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickString(out var value)) { + /// // `value` is of type `string` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickString([NotNullWhen(true)] out string? value) { value = this.Value as string; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBlocks(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBlocks([NotNullWhen(true)] out IReadOnlyList? value) { value = this.Value as IReadOnlyList; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch(System::Action @string, System::Action> blocks) { switch (this.Value) @@ -252,6 +241,27 @@ public void Switch(System::Action @string, System::Action + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (string value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match(System::Func @string, System::Func, T> blocks) { return this.Value switch @@ -269,6 +279,16 @@ public T Match(System::Func @string, System::Func value) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -278,6 +298,16 @@ public void Validate() ); } } + + public virtual bool Equals(ToolResultBlockParamContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; + } } sealed class ToolResultBlockParamContentConverter : JsonConverter @@ -408,30 +438,112 @@ public Block(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTextBlockParam(out var value)) { + /// // `value` is of type `TextBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTextBlockParam([NotNullWhen(true)] out TextBlockParam? value) { value = this.Value as TextBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickImageBlockParam(out var value)) { + /// // `value` is of type `ImageBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickImageBlockParam([NotNullWhen(true)] out ImageBlockParam? value) { value = this.Value as ImageBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickSearchResultBlockParam(out var value)) { + /// // `value` is of type `SearchResultBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickSearchResultBlockParam([NotNullWhen(true)] out SearchResultBlockParam? value) { value = this.Value as SearchResultBlockParam; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickDocumentBlockParam(out var value)) { + /// // `value` is of type `DocumentBlockParam` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickDocumentBlockParam([NotNullWhen(true)] out DocumentBlockParam? value) { value = this.Value as DocumentBlockParam; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (TextBlockParam value) => {...}, + /// (ImageBlockParam value) => {...}, + /// (SearchResultBlockParam value) => {...}, + /// (DocumentBlockParam value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action textBlockParam, System::Action imageBlockParam, @@ -458,6 +570,29 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (TextBlockParam value) => {...}, + /// (ImageBlockParam value) => {...}, + /// (SearchResultBlockParam value) => {...}, + /// (DocumentBlockParam value) => {...} + /// ); + /// + /// + /// public T Match( System::Func textBlockParam, System::Func imageBlockParam, @@ -483,12 +618,38 @@ public T Match( public static implicit operator Block(DocumentBlockParam value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of Block"); } + this.Switch( + (textBlockParam) => textBlockParam.Validate(), + (imageBlockParam) => imageBlockParam.Validate(), + (searchResultBlockParam) => searchResultBlockParam.Validate(), + (documentBlockParam) => documentBlockParam.Validate() + ); + } + + public virtual bool Equals(Block? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/ToolTextEditor20250124.cs b/src/Anthropic/Models/Messages/ToolTextEditor20250124.cs index b253d37f..e02c7942 100644 --- a/src/Anthropic/Models/Messages/ToolTextEditor20250124.cs +++ b/src/Anthropic/Models/Messages/ToolTextEditor20250124.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,44 +18,14 @@ public sealed record class ToolTextEditor20250124 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -66,23 +35,12 @@ public CacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "cache_control"); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { if ( @@ -112,6 +70,9 @@ public ToolTextEditor20250124() this.Type = JsonSerializer.Deserialize("\"text_editor_20250124\""); } + public ToolTextEditor20250124(ToolTextEditor20250124 toolTextEditor20250124) + : base(toolTextEditor20250124) { } + public ToolTextEditor20250124(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -128,6 +89,7 @@ public ToolTextEditor20250124(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ToolTextEditor20250124 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -138,6 +100,7 @@ IReadOnlyDictionary rawData class ToolTextEditor20250124FromRaw : IFromRaw { + /// public ToolTextEditor20250124 FromRawUnchecked( IReadOnlyDictionary rawData ) => ToolTextEditor20250124.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/ToolTextEditor20250429.cs b/src/Anthropic/Models/Messages/ToolTextEditor20250429.cs index 7e29f60d..576e93fd 100644 --- a/src/Anthropic/Models/Messages/ToolTextEditor20250429.cs +++ b/src/Anthropic/Models/Messages/ToolTextEditor20250429.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,44 +18,14 @@ public sealed record class ToolTextEditor20250429 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -66,23 +35,12 @@ public CacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "cache_control"); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { if ( @@ -112,6 +70,9 @@ public ToolTextEditor20250429() this.Type = JsonSerializer.Deserialize("\"text_editor_20250429\""); } + public ToolTextEditor20250429(ToolTextEditor20250429 toolTextEditor20250429) + : base(toolTextEditor20250429) { } + public ToolTextEditor20250429(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -128,6 +89,7 @@ public ToolTextEditor20250429(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ToolTextEditor20250429 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -138,6 +100,7 @@ IReadOnlyDictionary rawData class ToolTextEditor20250429FromRaw : IFromRaw { + /// public ToolTextEditor20250429 FromRawUnchecked( IReadOnlyDictionary rawData ) => ToolTextEditor20250429.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/ToolTextEditor20250728.cs b/src/Anthropic/Models/Messages/ToolTextEditor20250728.cs index c003c8c3..9e388941 100644 --- a/src/Anthropic/Models/Messages/ToolTextEditor20250728.cs +++ b/src/Anthropic/Models/Messages/ToolTextEditor20250728.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,44 +18,14 @@ public sealed record class ToolTextEditor20250728 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -66,21 +35,9 @@ public CacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "cache_control"); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -89,22 +46,11 @@ public CacheControlEphemeral? CacheControl /// public long? MaxCharacters { - get - { - if (!this._rawData.TryGetValue("max_characters", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["max_characters"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "max_characters"); } + init { ModelBase.Set(this._rawData, "max_characters", value); } } + /// public override void Validate() { if ( @@ -135,6 +81,9 @@ public ToolTextEditor20250728() this.Type = JsonSerializer.Deserialize("\"text_editor_20250728\""); } + public ToolTextEditor20250728(ToolTextEditor20250728 toolTextEditor20250728) + : base(toolTextEditor20250728) { } + public ToolTextEditor20250728(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -151,6 +100,7 @@ public ToolTextEditor20250728(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ToolTextEditor20250728 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -161,6 +111,7 @@ IReadOnlyDictionary rawData class ToolTextEditor20250728FromRaw : IFromRaw { + /// public ToolTextEditor20250728 FromRawUnchecked( IReadOnlyDictionary rawData ) => ToolTextEditor20250728.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/ToolUnion.cs b/src/Anthropic/Models/Messages/ToolUnion.cs index 6b3e9029..9d361a33 100644 --- a/src/Anthropic/Models/Messages/ToolUnion.cs +++ b/src/Anthropic/Models/Messages/ToolUnion.cs @@ -74,42 +74,156 @@ public ToolUnion(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTool(out var value)) { + /// // `value` is of type `Tool` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTool([NotNullWhen(true)] out Tool? value) { value = this.Value as Tool; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickBash20250124(out var value)) { + /// // `value` is of type `ToolBash20250124` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickBash20250124([NotNullWhen(true)] out ToolBash20250124? value) { value = this.Value as ToolBash20250124; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTextEditor20250124(out var value)) { + /// // `value` is of type `ToolTextEditor20250124` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTextEditor20250124([NotNullWhen(true)] out ToolTextEditor20250124? value) { value = this.Value as ToolTextEditor20250124; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTextEditor20250429(out var value)) { + /// // `value` is of type `ToolTextEditor20250429` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTextEditor20250429([NotNullWhen(true)] out ToolTextEditor20250429? value) { value = this.Value as ToolTextEditor20250429; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickTextEditor20250728(out var value)) { + /// // `value` is of type `ToolTextEditor20250728` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickTextEditor20250728([NotNullWhen(true)] out ToolTextEditor20250728? value) { value = this.Value as ToolTextEditor20250728; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickWebSearchTool20250305(out var value)) { + /// // `value` is of type `WebSearchTool20250305` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickWebSearchTool20250305([NotNullWhen(true)] out WebSearchTool20250305? value) { value = this.Value as WebSearchTool20250305; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (Tool value) => {...}, + /// (ToolBash20250124 value) => {...}, + /// (ToolTextEditor20250124 value) => {...}, + /// (ToolTextEditor20250429 value) => {...}, + /// (ToolTextEditor20250728 value) => {...}, + /// (WebSearchTool20250305 value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action tool, System::Action bash20250124, @@ -146,6 +260,31 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (Tool value) => {...}, + /// (ToolBash20250124 value) => {...}, + /// (ToolTextEditor20250124 value) => {...}, + /// (ToolTextEditor20250429 value) => {...}, + /// (ToolTextEditor20250728 value) => {...}, + /// (WebSearchTool20250305 value) => {...} + /// ); + /// + /// + /// public T Match( System::Func tool, System::Func bash20250124, @@ -181,12 +320,40 @@ public T Match( public static implicit operator ToolUnion(WebSearchTool20250305 value) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) { throw new AnthropicInvalidDataException("Data did not match any variant of ToolUnion"); } + this.Switch( + (tool) => tool.Validate(), + (bash20250124) => bash20250124.Validate(), + (textEditor20250124) => textEditor20250124.Validate(), + (textEditor20250429) => textEditor20250429.Validate(), + (textEditor20250728) => textEditor20250728.Validate(), + (webSearchTool20250305) => webSearchTool20250305.Validate() + ); + } + + public virtual bool Equals(ToolUnion? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/ToolUseBlock.cs b/src/Anthropic/Models/Messages/ToolUseBlock.cs index 5f54ff46..691939dd 100644 --- a/src/Anthropic/Models/Messages/ToolUseBlock.cs +++ b/src/Anthropic/Models/Messages/ToolUseBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,103 +13,35 @@ public sealed record class ToolUseBlock : ModelBase { public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } public required IReadOnlyDictionary Input { get { - if (!this._rawData.TryGetValue("input", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input' cannot be null", - new ArgumentOutOfRangeException("input", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'input' cannot be null", - new ArgumentNullException("input") - ); - } - init - { - this._rawData["input"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "input" ); } + init { ModelBase.Set(this._rawData, "input", value); } } public required string Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentNullException("name") - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ID; @@ -132,6 +63,9 @@ public ToolUseBlock() this.Type = JsonSerializer.Deserialize("\"tool_use\""); } + public ToolUseBlock(ToolUseBlock toolUseBlock) + : base(toolUseBlock) { } + public ToolUseBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -147,6 +81,7 @@ public ToolUseBlock(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ToolUseBlock FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -155,6 +90,7 @@ public static ToolUseBlock FromRawUnchecked(IReadOnlyDictionary { + /// public ToolUseBlock FromRawUnchecked(IReadOnlyDictionary rawData) => ToolUseBlock.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/ToolUseBlockParam.cs b/src/Anthropic/Models/Messages/ToolUseBlockParam.cs index a8b22327..e261bbc2 100644 --- a/src/Anthropic/Models/Messages/ToolUseBlockParam.cs +++ b/src/Anthropic/Models/Messages/ToolUseBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,101 +13,32 @@ public sealed record class ToolUseBlockParam : ModelBase { public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } public required IReadOnlyDictionary Input { get { - if (!this._rawData.TryGetValue("input", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input' cannot be null", - new ArgumentOutOfRangeException("input", "Missing required argument") - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'input' cannot be null", - new ArgumentNullException("input") - ); - } - init - { - this._rawData["input"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "input" ); } + init { ModelBase.Set(this._rawData, "input", value); } } public required string Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentNullException("name") - ); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -118,23 +48,12 @@ public CacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "cache_control"); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { _ = this.ID; @@ -157,6 +76,9 @@ public ToolUseBlockParam() this.Type = JsonSerializer.Deserialize("\"tool_use\""); } + public ToolUseBlockParam(ToolUseBlockParam toolUseBlockParam) + : base(toolUseBlockParam) { } + public ToolUseBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -172,6 +94,7 @@ public ToolUseBlockParam(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ToolUseBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -182,6 +105,7 @@ IReadOnlyDictionary rawData class ToolUseBlockParamFromRaw : IFromRaw { + /// public ToolUseBlockParam FromRawUnchecked(IReadOnlyDictionary rawData) => ToolUseBlockParam.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/URLImageSource.cs b/src/Anthropic/Models/Messages/URLImageSource.cs index 41b5ff62..e95284c2 100644 --- a/src/Anthropic/Models/Messages/URLImageSource.cs +++ b/src/Anthropic/Models/Messages/URLImageSource.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class URLImageSource : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required string URL { - get - { - if (!this._rawData.TryGetValue("url", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentOutOfRangeException("url", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentNullException("url") - ); - } - init - { - this._rawData["url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "url"); } + init { ModelBase.Set(this._rawData, "url", value); } } + /// public override void Validate() { if (!JsonElement.DeepEquals(this.Type, JsonSerializer.Deserialize("\"url\""))) @@ -72,6 +38,9 @@ public URLImageSource() this.Type = JsonSerializer.Deserialize("\"url\""); } + public URLImageSource(URLImageSource urlImageSource) + : base(urlImageSource) { } + public URLImageSource(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -87,6 +56,7 @@ public URLImageSource(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static URLImageSource FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -102,6 +72,7 @@ public URLImageSource(string url) class URLImageSourceFromRaw : IFromRaw { + /// public URLImageSource FromRawUnchecked(IReadOnlyDictionary rawData) => URLImageSource.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/URLPDFSource.cs b/src/Anthropic/Models/Messages/URLPDFSource.cs index 14a368b3..e614e9b7 100644 --- a/src/Anthropic/Models/Messages/URLPDFSource.cs +++ b/src/Anthropic/Models/Messages/URLPDFSource.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class URLPDFSource : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required string URL { - get - { - if (!this._rawData.TryGetValue("url", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentOutOfRangeException("url", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentNullException("url") - ); - } - init - { - this._rawData["url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "url"); } + init { ModelBase.Set(this._rawData, "url", value); } } + /// public override void Validate() { if (!JsonElement.DeepEquals(this.Type, JsonSerializer.Deserialize("\"url\""))) @@ -72,6 +38,9 @@ public URLPDFSource() this.Type = JsonSerializer.Deserialize("\"url\""); } + public URLPDFSource(URLPDFSource urlpdfSource) + : base(urlpdfSource) { } + public URLPDFSource(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -87,6 +56,7 @@ public URLPDFSource(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static URLPDFSource FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -102,6 +72,7 @@ public URLPDFSource(string url) class URLPDFSourceFromRaw : IFromRaw { + /// public URLPDFSource FromRawUnchecked(IReadOnlyDictionary rawData) => URLPDFSource.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/Usage.cs b/src/Anthropic/Models/Messages/Usage.cs index 2b1e0643..b21011c5 100644 --- a/src/Anthropic/Models/Messages/Usage.cs +++ b/src/Anthropic/Models/Messages/Usage.cs @@ -17,20 +17,8 @@ public sealed record class Usage : ModelBase /// public required CacheCreation? CacheCreation { - get - { - if (!this._rawData.TryGetValue("cache_creation", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["cache_creation"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "cache_creation"); } + init { ModelBase.Set(this._rawData, "cache_creation", value); } } /// @@ -40,18 +28,9 @@ public required long? CacheCreationInputTokens { get { - if (!this._rawData.TryGetValue("cache_creation_input_tokens", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["cache_creation_input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableStruct(this.RawData, "cache_creation_input_tokens"); } + init { ModelBase.Set(this._rawData, "cache_creation_input_tokens", value); } } /// @@ -59,20 +38,8 @@ public required long? CacheCreationInputTokens /// public required long? CacheReadInputTokens { - get - { - if (!this._rawData.TryGetValue("cache_read_input_tokens", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["cache_read_input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "cache_read_input_tokens"); } + init { ModelBase.Set(this._rawData, "cache_read_input_tokens", value); } } /// @@ -80,26 +47,8 @@ public required long? CacheReadInputTokens /// public required long InputTokens { - get - { - if (!this._rawData.TryGetValue("input_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'input_tokens' cannot be null", - new System::ArgumentOutOfRangeException( - "input_tokens", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["input_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "input_tokens"); } + init { ModelBase.Set(this._rawData, "input_tokens", value); } } /// @@ -107,26 +56,8 @@ public required long InputTokens /// public required long OutputTokens { - get - { - if (!this._rawData.TryGetValue("output_tokens", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'output_tokens' cannot be null", - new System::ArgumentOutOfRangeException( - "output_tokens", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["output_tokens"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "output_tokens"); } + init { ModelBase.Set(this._rawData, "output_tokens", value); } } /// @@ -134,23 +65,8 @@ public required long OutputTokens /// public required ServerToolUsage? ServerToolUse { - get - { - if (!this._rawData.TryGetValue("server_tool_use", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["server_tool_use"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "server_tool_use"); } + init { ModelBase.Set(this._rawData, "server_tool_use", value); } } /// @@ -160,23 +76,15 @@ public required ApiEnum? ServiceTier { get { - if (!this._rawData.TryGetValue("service_tier", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["service_tier"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>( + this.RawData, + "service_tier" ); } + init { ModelBase.Set(this._rawData, "service_tier", value); } } + /// public override void Validate() { this.CacheCreation?.Validate(); @@ -190,6 +98,9 @@ public override void Validate() public Usage() { } + public Usage(Usage usage) + : base(usage) { } + public Usage(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -203,6 +114,7 @@ public Usage(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static Usage FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -211,6 +123,7 @@ public static Usage FromRawUnchecked(IReadOnlyDictionary ra class UsageFromRaw : IFromRaw { + /// public Usage FromRawUnchecked(IReadOnlyDictionary rawData) => Usage.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/WebSearchResultBlock.cs b/src/Anthropic/Models/Messages/WebSearchResultBlock.cs index e8187643..442cd346 100644 --- a/src/Anthropic/Models/Messages/WebSearchResultBlock.cs +++ b/src/Anthropic/Models/Messages/WebSearchResultBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,121 +13,35 @@ public sealed record class WebSearchResultBlock : ModelBase { public required string EncryptedContent { - get - { - if (!this._rawData.TryGetValue("encrypted_content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'encrypted_content' cannot be null", - new ArgumentOutOfRangeException( - "encrypted_content", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'encrypted_content' cannot be null", - new ArgumentNullException("encrypted_content") - ); - } - init - { - this._rawData["encrypted_content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "encrypted_content"); } + init { ModelBase.Set(this._rawData, "encrypted_content", value); } } public required string? PageAge { - get - { - if (!this._rawData.TryGetValue("page_age", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["page_age"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "page_age"); } + init { ModelBase.Set(this._rawData, "page_age", value); } } public required string Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'title' cannot be null", - new ArgumentOutOfRangeException("title", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'title' cannot be null", - new ArgumentNullException("title") - ); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required string URL { - get - { - if (!this._rawData.TryGetValue("url", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentOutOfRangeException("url", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentNullException("url") - ); - } - init - { - this._rawData["url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "url"); } + init { ModelBase.Set(this._rawData, "url", value); } } + /// public override void Validate() { _ = this.EncryptedContent; @@ -151,6 +64,9 @@ public WebSearchResultBlock() this.Type = JsonSerializer.Deserialize("\"web_search_result\""); } + public WebSearchResultBlock(WebSearchResultBlock webSearchResultBlock) + : base(webSearchResultBlock) { } + public WebSearchResultBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -166,6 +82,7 @@ public WebSearchResultBlock(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static WebSearchResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -176,6 +93,7 @@ IReadOnlyDictionary rawData class WebSearchResultBlockFromRaw : IFromRaw { + /// public WebSearchResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => WebSearchResultBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/WebSearchResultBlockParam.cs b/src/Anthropic/Models/Messages/WebSearchResultBlockParam.cs index 556884c7..cbd12e9c 100644 --- a/src/Anthropic/Models/Messages/WebSearchResultBlockParam.cs +++ b/src/Anthropic/Models/Messages/WebSearchResultBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,121 +13,35 @@ public sealed record class WebSearchResultBlockParam : ModelBase { public required string EncryptedContent { - get - { - if (!this._rawData.TryGetValue("encrypted_content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'encrypted_content' cannot be null", - new ArgumentOutOfRangeException( - "encrypted_content", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'encrypted_content' cannot be null", - new ArgumentNullException("encrypted_content") - ); - } - init - { - this._rawData["encrypted_content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "encrypted_content"); } + init { ModelBase.Set(this._rawData, "encrypted_content", value); } } public required string Title { - get - { - if (!this._rawData.TryGetValue("title", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'title' cannot be null", - new ArgumentOutOfRangeException("title", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'title' cannot be null", - new ArgumentNullException("title") - ); - } - init - { - this._rawData["title"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "title"); } + init { ModelBase.Set(this._rawData, "title", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } public required string URL { - get - { - if (!this._rawData.TryGetValue("url", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentOutOfRangeException("url", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'url' cannot be null", - new ArgumentNullException("url") - ); - } - init - { - this._rawData["url"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "url"); } + init { ModelBase.Set(this._rawData, "url", value); } } public string? PageAge { - get - { - if (!this._rawData.TryGetValue("page_age", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["page_age"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "page_age"); } + init { ModelBase.Set(this._rawData, "page_age", value); } } + /// public override void Validate() { _ = this.EncryptedContent; @@ -151,6 +64,9 @@ public WebSearchResultBlockParam() this.Type = JsonSerializer.Deserialize("\"web_search_result\""); } + public WebSearchResultBlockParam(WebSearchResultBlockParam webSearchResultBlockParam) + : base(webSearchResultBlockParam) { } + public WebSearchResultBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -166,6 +82,7 @@ public WebSearchResultBlockParam(IReadOnlyDictionary rawDat } #pragma warning restore CS8618 + /// public static WebSearchResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -176,6 +93,7 @@ IReadOnlyDictionary rawData class WebSearchResultBlockParamFromRaw : IFromRaw { + /// public WebSearchResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => WebSearchResultBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/WebSearchTool20250305.cs b/src/Anthropic/Models/Messages/WebSearchTool20250305.cs index 39f684ba..5b00d8b1 100644 --- a/src/Anthropic/Models/Messages/WebSearchTool20250305.cs +++ b/src/Anthropic/Models/Messages/WebSearchTool20250305.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -19,44 +18,14 @@ public sealed record class WebSearchTool20250305 : ModelBase /// public JsonElement Name { - get - { - if (!this._rawData.TryGetValue("name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'name' cannot be null", - new ArgumentOutOfRangeException("name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "name"); } + init { ModelBase.Set(this._rawData, "name", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -65,20 +34,8 @@ public JsonElement Type /// public IReadOnlyList? AllowedDomains { - get - { - if (!this._rawData.TryGetValue("allowed_domains", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["allowed_domains"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "allowed_domains"); } + init { ModelBase.Set(this._rawData, "allowed_domains", value); } } /// @@ -86,20 +43,8 @@ public IReadOnlyList? AllowedDomains /// public IReadOnlyList? BlockedDomains { - get - { - if (!this._rawData.TryGetValue("blocked_domains", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize?>(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["blocked_domains"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass>(this.RawData, "blocked_domains"); } + init { ModelBase.Set(this._rawData, "blocked_domains", value); } } /// @@ -109,21 +54,9 @@ public CacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "cache_control"); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } /// @@ -131,20 +64,8 @@ public CacheControlEphemeral? CacheControl /// public long? MaxUses { - get - { - if (!this._rawData.TryGetValue("max_uses", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["max_uses"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableStruct(this.RawData, "max_uses"); } + init { ModelBase.Set(this._rawData, "max_uses", value); } } /// @@ -152,22 +73,11 @@ public long? MaxUses /// public UserLocation? UserLocation { - get - { - if (!this._rawData.TryGetValue("user_location", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["user_location"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "user_location"); } + init { ModelBase.Set(this._rawData, "user_location", value); } } + /// public override void Validate() { if ( @@ -201,6 +111,9 @@ public WebSearchTool20250305() this.Type = JsonSerializer.Deserialize("\"web_search_20250305\""); } + public WebSearchTool20250305(WebSearchTool20250305 webSearchTool20250305) + : base(webSearchTool20250305) { } + public WebSearchTool20250305(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -217,6 +130,7 @@ public WebSearchTool20250305(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static WebSearchTool20250305 FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -227,6 +141,7 @@ IReadOnlyDictionary rawData class WebSearchTool20250305FromRaw : IFromRaw { + /// public WebSearchTool20250305 FromRawUnchecked( IReadOnlyDictionary rawData ) => WebSearchTool20250305.FromRawUnchecked(rawData); @@ -240,23 +155,8 @@ public sealed record class UserLocation : ModelBase { public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -264,20 +164,8 @@ public JsonElement Type /// public string? City { - get - { - if (!this._rawData.TryGetValue("city", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["city"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "city"); } + init { ModelBase.Set(this._rawData, "city", value); } } /// @@ -286,20 +174,8 @@ public string? City /// public string? Country { - get - { - if (!this._rawData.TryGetValue("country", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["country"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "country"); } + init { ModelBase.Set(this._rawData, "country", value); } } /// @@ -307,20 +183,8 @@ public string? Country /// public string? Region { - get - { - if (!this._rawData.TryGetValue("region", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["region"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "region"); } + init { ModelBase.Set(this._rawData, "region", value); } } /// @@ -328,22 +192,11 @@ public string? Region /// public string? Timezone { - get - { - if (!this._rawData.TryGetValue("timezone", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["timezone"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "timezone"); } + init { ModelBase.Set(this._rawData, "timezone", value); } } + /// public override void Validate() { if ( @@ -366,6 +219,9 @@ public UserLocation() this.Type = JsonSerializer.Deserialize("\"approximate\""); } + public UserLocation(UserLocation userLocation) + : base(userLocation) { } + public UserLocation(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -381,6 +237,7 @@ public UserLocation(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static UserLocation FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -389,6 +246,7 @@ public static UserLocation FromRawUnchecked(IReadOnlyDictionary { + /// public UserLocation FromRawUnchecked(IReadOnlyDictionary rawData) => UserLocation.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Messages/WebSearchToolRequestError.cs b/src/Anthropic/Models/Messages/WebSearchToolRequestError.cs index 9a05d690..cf067d00 100644 --- a/src/Anthropic/Models/Messages/WebSearchToolRequestError.cs +++ b/src/Anthropic/Models/Messages/WebSearchToolRequestError.cs @@ -16,50 +16,21 @@ public required ApiEnum ErrorCode { get { - if (!this._rawData.TryGetValue("error_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error_code' cannot be null", - new System::ArgumentOutOfRangeException( - "error_code", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["error_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "error_code" ); } + init { ModelBase.Set(this._rawData, "error_code", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.ErrorCode.Validate(); @@ -79,6 +50,9 @@ public WebSearchToolRequestError() this.Type = JsonSerializer.Deserialize("\"web_search_tool_result_error\""); } + public WebSearchToolRequestError(WebSearchToolRequestError webSearchToolRequestError) + : base(webSearchToolRequestError) { } + public WebSearchToolRequestError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -94,6 +68,7 @@ public WebSearchToolRequestError(IReadOnlyDictionary rawDat } #pragma warning restore CS8618 + /// public static WebSearchToolRequestError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -111,6 +86,7 @@ public WebSearchToolRequestError(ApiEnum errorCode) class WebSearchToolRequestErrorFromRaw : IFromRaw { + /// public WebSearchToolRequestError FromRawUnchecked( IReadOnlyDictionary rawData ) => WebSearchToolRequestError.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/WebSearchToolResultBlock.cs b/src/Anthropic/Models/Messages/WebSearchToolResultBlock.cs index a4c9b4ef..ea0e1173 100644 --- a/src/Anthropic/Models/Messages/WebSearchToolResultBlock.cs +++ b/src/Anthropic/Models/Messages/WebSearchToolResultBlock.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -16,76 +15,27 @@ public required WebSearchToolResultBlockContent Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new ArgumentOutOfRangeException("tool_use_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -106,6 +56,9 @@ public WebSearchToolResultBlock() this.Type = JsonSerializer.Deserialize("\"web_search_tool_result\""); } + public WebSearchToolResultBlock(WebSearchToolResultBlock webSearchToolResultBlock) + : base(webSearchToolResultBlock) { } + public WebSearchToolResultBlock(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -121,6 +74,7 @@ public WebSearchToolResultBlock(IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static WebSearchToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -131,6 +85,7 @@ IReadOnlyDictionary rawData class WebSearchToolResultBlockFromRaw : IFromRaw { + /// public WebSearchToolResultBlock FromRawUnchecked( IReadOnlyDictionary rawData ) => WebSearchToolResultBlock.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/WebSearchToolResultBlockContent.cs b/src/Anthropic/Models/Messages/WebSearchToolResultBlockContent.cs index f63215fd..6f086f70 100644 --- a/src/Anthropic/Models/Messages/WebSearchToolResultBlockContent.cs +++ b/src/Anthropic/Models/Messages/WebSearchToolResultBlockContent.cs @@ -40,12 +40,42 @@ public WebSearchToolResultBlockContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickError(out var value)) { + /// // `value` is of type `WebSearchToolResultError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickError([NotNullWhen(true)] out WebSearchToolResultError? value) { value = this.Value as WebSearchToolResultError; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickWebSearchResultBlocks(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickWebSearchResultBlocks( [NotNullWhen(true)] out IReadOnlyList? value ) @@ -54,6 +84,26 @@ public bool TryPickWebSearchResultBlocks( return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (WebSearchToolResultError value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action error, System::Action> webSearchResultBlocks @@ -74,6 +124,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (WebSearchToolResultError value) => {...}, + /// (IReadOnlyList value) => {...} + /// ); + /// + /// + /// public T Match( System::Func error, System::Func, T> webSearchResultBlocks @@ -97,6 +168,16 @@ public static implicit operator WebSearchToolResultBlockContent( List value ) => new((IReadOnlyList)value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -105,6 +186,17 @@ public void Validate() "Data did not match any variant of WebSearchToolResultBlockContent" ); } + this.Switch((error) => error.Validate(), (_) => { }); + } + + public virtual bool Equals(WebSearchToolResultBlockContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/WebSearchToolResultBlockParam.cs b/src/Anthropic/Models/Messages/WebSearchToolResultBlockParam.cs index fe67c89d..a875d29d 100644 --- a/src/Anthropic/Models/Messages/WebSearchToolResultBlockParam.cs +++ b/src/Anthropic/Models/Messages/WebSearchToolResultBlockParam.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -18,74 +17,24 @@ public required WebSearchToolResultBlockParamContent Content { get { - if (!this._rawData.TryGetValue("content", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentOutOfRangeException("content", "Missing required argument") - ); - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ) - ?? throw new AnthropicInvalidDataException( - "'content' cannot be null", - new ArgumentNullException("content") - ); - } - init - { - this._rawData["content"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass( + this.RawData, + "content" ); } + init { ModelBase.Set(this._rawData, "content", value); } } public required string ToolUseID { - get - { - if (!this._rawData.TryGetValue("tool_use_id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new ArgumentOutOfRangeException("tool_use_id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'tool_use_id' cannot be null", - new ArgumentNullException("tool_use_id") - ); - } - init - { - this._rawData["tool_use_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "tool_use_id"); } + init { ModelBase.Set(this._rawData, "tool_use_id", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } /// @@ -95,23 +44,12 @@ public CacheControlEphemeral? CacheControl { get { - if (!this._rawData.TryGetValue("cache_control", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["cache_control"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + return ModelBase.GetNullableClass(this.RawData, "cache_control"); } + init { ModelBase.Set(this._rawData, "cache_control", value); } } + /// public override void Validate() { this.Content.Validate(); @@ -133,6 +71,11 @@ public WebSearchToolResultBlockParam() this.Type = JsonSerializer.Deserialize("\"web_search_tool_result\""); } + public WebSearchToolResultBlockParam( + WebSearchToolResultBlockParam webSearchToolResultBlockParam + ) + : base(webSearchToolResultBlockParam) { } + public WebSearchToolResultBlockParam(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -148,6 +91,7 @@ public WebSearchToolResultBlockParam(IReadOnlyDictionary ra } #pragma warning restore CS8618 + /// public static WebSearchToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -158,6 +102,7 @@ IReadOnlyDictionary rawData class WebSearchToolResultBlockParamFromRaw : IFromRaw { + /// public WebSearchToolResultBlockParam FromRawUnchecked( IReadOnlyDictionary rawData ) => WebSearchToolResultBlockParam.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Messages/WebSearchToolResultBlockParamContent.cs b/src/Anthropic/Models/Messages/WebSearchToolResultBlockParamContent.cs index 22e4e727..02a99590 100644 --- a/src/Anthropic/Models/Messages/WebSearchToolResultBlockParamContent.cs +++ b/src/Anthropic/Models/Messages/WebSearchToolResultBlockParamContent.cs @@ -43,18 +43,68 @@ public WebSearchToolResultBlockParamContent(JsonElement json) this._json = json; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickItem(out var value)) { + /// // `value` is of type `IReadOnlyList` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickItem([NotNullWhen(true)] out IReadOnlyList? value) { value = this.Value as IReadOnlyList; return value != null; } + /// + /// Returns true and sets the out parameter if the instance was constructed with a variant of + /// type . + /// + /// Consider using or if you need to handle every variant. + /// + /// + /// + /// if (instance.TryPickRequestError(out var value)) { + /// // `value` is of type `WebSearchToolRequestError` + /// Console.WriteLine(value); + /// } + /// + /// + /// public bool TryPickRequestError([NotNullWhen(true)] out WebSearchToolRequestError? value) { value = this.Value as WebSearchToolRequestError; return value != null; } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you need your function parameters to return something. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// instance.Switch( + /// (IReadOnlyList value) => {...}, + /// (WebSearchToolRequestError value) => {...} + /// ); + /// + /// + /// public void Switch( System::Action> webSearchToolResultBlockItem, System::Action requestError @@ -75,6 +125,27 @@ public void Switch( } } + /// + /// Calls the function parameter corresponding to the variant the instance was constructed with and + /// returns its result. + /// + /// Use the TryPick method(s) if you don't need to handle every variant, or + /// if you don't need your function parameters to return a value. + /// + /// + /// Thrown when the instance was constructed with an unknown variant (e.g. deserialized from raw data + /// that doesn't match any variant's expected shape). + /// + /// + /// + /// + /// var result = instance.Match( + /// (IReadOnlyList value) => {...}, + /// (WebSearchToolRequestError value) => {...} + /// ); + /// + /// + /// public T Match( System::Func, T> webSearchToolResultBlockItem, System::Func requestError @@ -98,6 +169,16 @@ public static implicit operator WebSearchToolResultBlockParamContent( WebSearchToolRequestError value ) => new(value); + /// + /// Validates that the instance was constructed with a known variant and that this variant is valid + /// (based on its own Validate method). + /// + /// This is useful for instances constructed from raw JSON data (e.g. deserialized from an API response). + /// + /// + /// Thrown when the instance does not pass validation. + /// + /// public void Validate() { if (this.Value == null) @@ -106,6 +187,17 @@ public void Validate() "Data did not match any variant of WebSearchToolResultBlockParamContent" ); } + this.Switch((_) => { }, (requestError) => requestError.Validate()); + } + + public virtual bool Equals(WebSearchToolResultBlockParamContent? other) + { + return other != null && JsonElement.DeepEquals(this.Json, other.Json); + } + + public override int GetHashCode() + { + return 0; } } diff --git a/src/Anthropic/Models/Messages/WebSearchToolResultError.cs b/src/Anthropic/Models/Messages/WebSearchToolResultError.cs index 876c76aa..ef7238fc 100644 --- a/src/Anthropic/Models/Messages/WebSearchToolResultError.cs +++ b/src/Anthropic/Models/Messages/WebSearchToolResultError.cs @@ -16,50 +16,21 @@ public required ApiEnum ErrorCode { get { - if (!this._rawData.TryGetValue("error_code", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'error_code' cannot be null", - new System::ArgumentOutOfRangeException( - "error_code", - "Missing required argument" - ) - ); - - return JsonSerializer.Deserialize>( - element, - ModelBase.SerializerOptions - ); - } - init - { - this._rawData["error_code"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions + return ModelBase.GetNotNullClass>( + this.RawData, + "error_code" ); } + init { ModelBase.Set(this._rawData, "error_code", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new System::ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { this.ErrorCode.Validate(); @@ -79,6 +50,9 @@ public WebSearchToolResultError() this.Type = JsonSerializer.Deserialize("\"web_search_tool_result_error\""); } + public WebSearchToolResultError(WebSearchToolResultError webSearchToolResultError) + : base(webSearchToolResultError) { } + public WebSearchToolResultError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -94,6 +68,7 @@ public WebSearchToolResultError(IReadOnlyDictionary rawData } #pragma warning restore CS8618 + /// public static WebSearchToolResultError FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -111,6 +86,7 @@ public WebSearchToolResultError(ApiEnum { + /// public WebSearchToolResultError FromRawUnchecked( IReadOnlyDictionary rawData ) => WebSearchToolResultError.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Models/ModelInfo.cs b/src/Anthropic/Models/Models/ModelInfo.cs index e251e288..c7a248d9 100644 --- a/src/Anthropic/Models/Models/ModelInfo.cs +++ b/src/Anthropic/Models/Models/ModelInfo.cs @@ -17,27 +17,8 @@ public sealed record class ModelInfo : ModelBase /// public required string ID { - get - { - if (!this._rawData.TryGetValue("id", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentOutOfRangeException("id", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'id' cannot be null", - new ArgumentNullException("id") - ); - } - init - { - this._rawData["id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "id"); } + init { ModelBase.Set(this._rawData, "id", value); } } /// @@ -46,23 +27,8 @@ public required string ID /// public required DateTimeOffset CreatedAt { - get - { - if (!this._rawData.TryGetValue("created_at", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'created_at' cannot be null", - new ArgumentOutOfRangeException("created_at", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["created_at"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "created_at"); } + init { ModelBase.Set(this._rawData, "created_at", value); } } /// @@ -70,27 +36,8 @@ public required DateTimeOffset CreatedAt /// public required string DisplayName { - get - { - if (!this._rawData.TryGetValue("display_name", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'display_name' cannot be null", - new ArgumentOutOfRangeException("display_name", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'display_name' cannot be null", - new ArgumentNullException("display_name") - ); - } - init - { - this._rawData["display_name"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "display_name"); } + init { ModelBase.Set(this._rawData, "display_name", value); } } /// @@ -100,25 +47,11 @@ public required string DisplayName /// public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.ID; @@ -137,6 +70,9 @@ public ModelInfo() this.Type = JsonSerializer.Deserialize("\"model\""); } + public ModelInfo(ModelInfo modelInfo) + : base(modelInfo) { } + public ModelInfo(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -152,6 +88,7 @@ public ModelInfo(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ModelInfo FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -160,6 +97,7 @@ public static ModelInfo FromRawUnchecked(IReadOnlyDictionary { + /// public ModelInfo FromRawUnchecked(IReadOnlyDictionary rawData) => ModelInfo.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/Models/ModelListPageResponse.cs b/src/Anthropic/Models/Models/ModelListPageResponse.cs index 750bc6cd..17be8e51 100644 --- a/src/Anthropic/Models/Models/ModelListPageResponse.cs +++ b/src/Anthropic/Models/Models/ModelListPageResponse.cs @@ -1,11 +1,9 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; using Anthropic.Core; -using Anthropic.Exceptions; namespace Anthropic.Models.Models; @@ -14,27 +12,8 @@ public sealed record class ModelListPageResponse : ModelBase { public required IReadOnlyList Data { - get - { - if (!this._rawData.TryGetValue("data", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentOutOfRangeException("data", "Missing required argument") - ); - - return JsonSerializer.Deserialize>(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'data' cannot be null", - new ArgumentNullException("data") - ); - } - init - { - this._rawData["data"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass>(this.RawData, "data"); } + init { ModelBase.Set(this._rawData, "data", value); } } /// @@ -42,20 +21,8 @@ public required IReadOnlyList Data /// public required string? FirstID { - get - { - if (!this._rawData.TryGetValue("first_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["first_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "first_id"); } + init { ModelBase.Set(this._rawData, "first_id", value); } } /// @@ -63,23 +30,8 @@ public required string? FirstID /// public required bool HasMore { - get - { - if (!this._rawData.TryGetValue("has_more", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'has_more' cannot be null", - new ArgumentOutOfRangeException("has_more", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["has_more"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "has_more"); } + init { ModelBase.Set(this._rawData, "has_more", value); } } /// @@ -87,22 +39,11 @@ public required bool HasMore /// public required string? LastID { - get - { - if (!this._rawData.TryGetValue("last_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["last_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNullableClass(this.RawData, "last_id"); } + init { ModelBase.Set(this._rawData, "last_id", value); } } + /// public override void Validate() { foreach (var item in this.Data) @@ -116,6 +57,9 @@ public override void Validate() public ModelListPageResponse() { } + public ModelListPageResponse(ModelListPageResponse modelListPageResponse) + : base(modelListPageResponse) { } + public ModelListPageResponse(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -129,6 +73,7 @@ public ModelListPageResponse(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static ModelListPageResponse FromRawUnchecked( IReadOnlyDictionary rawData ) @@ -139,6 +84,7 @@ IReadOnlyDictionary rawData class ModelListPageResponseFromRaw : IFromRaw { + /// public ModelListPageResponse FromRawUnchecked( IReadOnlyDictionary rawData ) => ModelListPageResponse.FromRawUnchecked(rawData); diff --git a/src/Anthropic/Models/Models/ModelListParams.cs b/src/Anthropic/Models/Models/ModelListParams.cs index bef7eaa1..17958ba3 100644 --- a/src/Anthropic/Models/Models/ModelListParams.cs +++ b/src/Anthropic/Models/Models/ModelListParams.cs @@ -23,13 +23,7 @@ public sealed record class ModelListParams : ParamsBase /// public string? AfterID { - get - { - if (!this._rawQueryData.TryGetValue("after_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawQueryData, "after_id"); } init { if (value == null) @@ -37,10 +31,7 @@ public string? AfterID return; } - this._rawQueryData["after_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "after_id", value); } } @@ -50,13 +41,7 @@ public string? AfterID /// public string? BeforeID { - get - { - if (!this._rawQueryData.TryGetValue("before_id", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableClass(this.RawQueryData, "before_id"); } init { if (value == null) @@ -64,10 +49,7 @@ public string? BeforeID return; } - this._rawQueryData["before_id"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "before_id", value); } } @@ -78,13 +60,7 @@ public string? BeforeID /// public long? Limit { - get - { - if (!this._rawQueryData.TryGetValue("limit", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } + get { return ModelBase.GetNullableStruct(this.RawQueryData, "limit"); } init { if (value == null) @@ -92,10 +68,7 @@ public long? Limit return; } - this._rawQueryData["limit"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawQueryData, "limit", value); } } @@ -106,12 +79,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -121,15 +91,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public ModelListParams() { } + public ModelListParams(ModelListParams modelListParams) + : base(modelListParams) { } + public ModelListParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -151,6 +121,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static ModelListParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/Models/ModelRetrieveParams.cs b/src/Anthropic/Models/Models/ModelRetrieveParams.cs index 36bd1b0f..c774e41b 100644 --- a/src/Anthropic/Models/Models/ModelRetrieveParams.cs +++ b/src/Anthropic/Models/Models/ModelRetrieveParams.cs @@ -26,12 +26,9 @@ public IReadOnlyList>? Betas { get { - if (!this._rawHeaderData.TryGetValue("anthropic-beta", out JsonElement element)) - return null; - - return JsonSerializer.Deserialize>?>( - element, - ModelBase.SerializerOptions + return ModelBase.GetNullableClass>>( + this.RawHeaderData, + "anthropic-beta" ); } init @@ -41,15 +38,15 @@ public IReadOnlyList>? Betas return; } - this._rawHeaderData["anthropic-beta"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); + ModelBase.Set(this._rawHeaderData, "anthropic-beta", value); } } public ModelRetrieveParams() { } + public ModelRetrieveParams(ModelRetrieveParams modelRetrieveParams) + : base(modelRetrieveParams) { } + public ModelRetrieveParams( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData @@ -71,6 +68,7 @@ FrozenDictionary rawQueryData } #pragma warning restore CS8618 + /// public static ModelRetrieveParams FromRawUnchecked( IReadOnlyDictionary rawHeaderData, IReadOnlyDictionary rawQueryData diff --git a/src/Anthropic/Models/NotFoundError.cs b/src/Anthropic/Models/NotFoundError.cs index 17f3807c..86b45cda 100644 --- a/src/Anthropic/Models/NotFoundError.cs +++ b/src/Anthropic/Models/NotFoundError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class NotFoundError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public NotFoundError() this.Type = JsonSerializer.Deserialize("\"not_found_error\""); } + public NotFoundError(NotFoundError notFoundError) + : base(notFoundError) { } + public NotFoundError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public NotFoundError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static NotFoundError FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -107,6 +77,7 @@ public NotFoundError(string message) class NotFoundErrorFromRaw : IFromRaw { + /// public NotFoundError FromRawUnchecked(IReadOnlyDictionary rawData) => NotFoundError.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/OverloadedError.cs b/src/Anthropic/Models/OverloadedError.cs index df335c73..66015c0a 100644 --- a/src/Anthropic/Models/OverloadedError.cs +++ b/src/Anthropic/Models/OverloadedError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class OverloadedError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public OverloadedError() this.Type = JsonSerializer.Deserialize("\"overloaded_error\""); } + public OverloadedError(OverloadedError overloadedError) + : base(overloadedError) { } + public OverloadedError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public OverloadedError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static OverloadedError FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -107,6 +77,7 @@ public OverloadedError(string message) class OverloadedErrorFromRaw : IFromRaw { + /// public OverloadedError FromRawUnchecked(IReadOnlyDictionary rawData) => OverloadedError.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/PermissionError.cs b/src/Anthropic/Models/PermissionError.cs index 3d1ad412..3c64381c 100644 --- a/src/Anthropic/Models/PermissionError.cs +++ b/src/Anthropic/Models/PermissionError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class PermissionError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public PermissionError() this.Type = JsonSerializer.Deserialize("\"permission_error\""); } + public PermissionError(PermissionError permissionError) + : base(permissionError) { } + public PermissionError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public PermissionError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static PermissionError FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -107,6 +77,7 @@ public PermissionError(string message) class PermissionErrorFromRaw : IFromRaw { + /// public PermissionError FromRawUnchecked(IReadOnlyDictionary rawData) => PermissionError.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Models/RateLimitError.cs b/src/Anthropic/Models/RateLimitError.cs index cd5f1481..d1a9018e 100644 --- a/src/Anthropic/Models/RateLimitError.cs +++ b/src/Anthropic/Models/RateLimitError.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Frozen; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; @@ -14,50 +13,17 @@ public sealed record class RateLimitError : ModelBase { public required string Message { - get - { - if (!this._rawData.TryGetValue("message", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentOutOfRangeException("message", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions) - ?? throw new AnthropicInvalidDataException( - "'message' cannot be null", - new ArgumentNullException("message") - ); - } - init - { - this._rawData["message"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullClass(this.RawData, "message"); } + init { ModelBase.Set(this._rawData, "message", value); } } public JsonElement Type { - get - { - if (!this._rawData.TryGetValue("type", out JsonElement element)) - throw new AnthropicInvalidDataException( - "'type' cannot be null", - new ArgumentOutOfRangeException("type", "Missing required argument") - ); - - return JsonSerializer.Deserialize(element, ModelBase.SerializerOptions); - } - init - { - this._rawData["type"] = JsonSerializer.SerializeToElement( - value, - ModelBase.SerializerOptions - ); - } + get { return ModelBase.GetNotNullStruct(this.RawData, "type"); } + init { ModelBase.Set(this._rawData, "type", value); } } + /// public override void Validate() { _ = this.Message; @@ -77,6 +43,9 @@ public RateLimitError() this.Type = JsonSerializer.Deserialize("\"rate_limit_error\""); } + public RateLimitError(RateLimitError rateLimitError) + : base(rateLimitError) { } + public RateLimitError(IReadOnlyDictionary rawData) { this._rawData = [.. rawData]; @@ -92,6 +61,7 @@ public RateLimitError(IReadOnlyDictionary rawData) } #pragma warning restore CS8618 + /// public static RateLimitError FromRawUnchecked(IReadOnlyDictionary rawData) { return new(FrozenDictionary.ToFrozenDictionary(rawData)); @@ -107,6 +77,7 @@ public RateLimitError(string message) class RateLimitErrorFromRaw : IFromRaw { + /// public RateLimitError FromRawUnchecked(IReadOnlyDictionary rawData) => RateLimitError.FromRawUnchecked(rawData); } diff --git a/src/Anthropic/Services/Beta/FileService.cs b/src/Anthropic/Services/Beta/FileService.cs index 5ae0fedc..035a8267 100644 --- a/src/Anthropic/Services/Beta/FileService.cs +++ b/src/Anthropic/Services/Beta/FileService.cs @@ -8,7 +8,7 @@ namespace Anthropic.Services.Beta; -/// +/// public sealed class FileService : IFileService { internal static void AddDefaultHeaders(HttpRequestMessage request) diff --git a/src/Anthropic/Services/Beta/MessageService.cs b/src/Anthropic/Services/Beta/MessageService.cs index 0aaacc91..401e1f05 100644 --- a/src/Anthropic/Services/Beta/MessageService.cs +++ b/src/Anthropic/Services/Beta/MessageService.cs @@ -12,7 +12,7 @@ namespace Anthropic.Services.Beta; -/// +/// public sealed class MessageService : global::Anthropic.Services.Beta.IMessageService { /// @@ -97,9 +97,13 @@ options with ) .Execute(request, cancellationToken) .ConfigureAwait(false); - await foreach (var message in SseMessage.GetEnumerable(response.Message, cancellationToken)) + await foreach ( + var betaMessage in Sse.Enumerate( + response.Message, + cancellationToken + ) + ) { - var betaMessage = message.Deserialize(); if (this._client.ResponseValidation) { betaMessage.Validate(); diff --git a/src/Anthropic/Services/Beta/Messages/AnthropicBetaClientExtensions.cs b/src/Anthropic/Services/Beta/Messages/AnthropicBetaClientExtensions.cs index d2aacf1c..e0579b90 100644 --- a/src/Anthropic/Services/Beta/Messages/AnthropicBetaClientExtensions.cs +++ b/src/Anthropic/Services/Beta/Messages/AnthropicBetaClientExtensions.cs @@ -9,6 +9,7 @@ using System.Threading; using System.Threading.Tasks; using Anthropic.Core; +using Anthropic.Models.Beta; using Anthropic.Models.Beta.Messages; using Anthropic.Services.Beta; @@ -19,6 +20,52 @@ namespace Microsoft.Extensions.AI; public static class AnthropicBetaClientExtensions { + /// + /// Creates an to represent a skill for use with the Anthropic Skills API. + /// + /// The skill parameters to wrap as an . + /// The wrapped as an . + /// + /// + /// The returned tool is only suitable for use with the returned by + /// (or s that delegate + /// to such an instance). It is likely to be ignored by any other implementation. + /// + /// + /// When this tool is included in , the will automatically: + /// + /// Configure the container with the skill(s) + /// Add the required beta headers (code-execution-2025-08-25 and skills-2025-10-02) + /// Add the code execution tool if not already present + /// + /// + /// + /// Example usage: + /// + /// var options = new ChatOptions + /// { + /// ModelId = "claude-sonnet-4-5-20250929", + /// MaxOutputTokens = 4096, + /// Tools = + /// [ + /// new BetaSkillParams { Type = BetaSkillParamsType.Anthropic, SkillID = "pptx", Version = "latest" }.AsAITool(), + /// new BetaSkillParams { Type = BetaSkillParamsType.Anthropic, SkillID = "xlsx", Version = "latest" }.AsAITool(), + /// ] + /// }; + /// + /// + /// + /// is . + public static AITool AsAITool(this BetaSkillParams skillParams) + { + if (skillParams is null) + { + throw new ArgumentNullException(nameof(skillParams)); + } + + return new BetaSkillsParamsAITool(skillParams); + } + /// Gets an for use with this . /// The beta service. /// @@ -80,7 +127,7 @@ public static AITool AsAITool(this BetaToolUnion tool) throw new ArgumentNullException(nameof(tool)); } - return new ToolUnionAITool(tool); + return new BetaToolUnionAITool(tool); } private sealed class AnthropicChatClient( @@ -392,6 +439,8 @@ out var functionData ) ); } + + streamingFunctions.Clear(); } break; } @@ -810,6 +859,11 @@ private MessageCreateParams GetMessageCreateParams( }; } + HashSet? betaHeaders = createParams.Betas is { Count: > 0 } + ? [.. createParams.Betas] + : null; + int originalBetaHeadersCount = betaHeaders?.Count ?? 0; + if (options is not null) { if (options.Instructions is { } instructions) @@ -886,11 +940,19 @@ createParams.OutputFormat is null List? createdTools = createParams.Tools?.ToList(); List? mcpServers = createParams.MCPServers?.ToList(); + List? skills = null; foreach (var tool in tools) { switch (tool) { - case ToolUnionAITool raw: + case BetaSkillsParamsAITool skillTool: + (betaHeaders ??= []).Add("skills-2025-10-02"); + betaHeaders.Add("code-execution-2025-08-25"); + + (skills ??= []).Add(skillTool.SkillParams); + break; + + case BetaToolUnionAITool raw: (createdTools ??= []).Add(raw.Tool); break; @@ -951,7 +1013,7 @@ r.ValueKind is JsonValueKind.String List> >(af, nameof(BetaTool.InputExamples)), AllowedCallers = GetValue< - List> + List> >(af, nameof(BetaTool.AllowedCallers)), } ); @@ -969,10 +1031,12 @@ is true break; case HostedCodeInterpreterTool: + (betaHeaders ??= []).Add("code-execution-2025-08-25"); (createdTools ??= []).Add(new BetaCodeExecutionTool20250825()); break; case HostedMcpServerTool mcp: + (betaHeaders ??= []).Add("mcp-client-2025-11-20"); (mcpServers ??= []).Add( mcp.AllowedTools is { Count: > 0 } allowedTools ? new() @@ -991,6 +1055,36 @@ is true } } + if (skills?.Count > 0) + { + // Merge with any existing skills in the container + if ( + createParams.Container is { } existingContainer + && existingContainer.TryPickBetaContainerParams( + out var existingContainerParams + ) + && existingContainerParams.Skills is { Count: > 0 } existingSkills + ) + { + skills.InsertRange(0, existingSkills); + } + + createParams = createParams with + { + Container = new BetaContainerParams() { Skills = skills }, + }; + + // Ensure code execution tool is present + bool hasCodeExecutionTool = + createdTools?.Any(t => t.Value is BetaCodeExecutionTool20250825) + == true; + if (!hasCodeExecutionTool) + { + (betaHeaders ??= []).Add("code-execution-2025-08-25"); + (createdTools ??= []).Add(new BetaCodeExecutionTool20250825()); + } + } + if (createdTools?.Count > 0) { createParams = createParams with { Tools = createdTools }; @@ -1046,6 +1140,11 @@ existingSystem.Value is IReadOnlyList existingMessages createParams = createParams with { System = systemMessages }; } + if (betaHeaders is not null && betaHeaders.Count != originalBetaHeadersCount) + { + createParams = createParams with { Betas = [.. betaHeaders] }; + } + return createParams; } @@ -1343,7 +1442,7 @@ private sealed class StreamingFunctionData } } - private sealed class ToolUnionAITool(BetaToolUnion tool) : AITool + private sealed class BetaToolUnionAITool(BetaToolUnion tool) : AITool { public BetaToolUnion Tool => tool; @@ -1354,4 +1453,16 @@ private sealed class ToolUnionAITool(BetaToolUnion tool) : AITool ? tool : base.GetService(serviceType!, serviceKey); } + + private sealed class BetaSkillsParamsAITool(BetaSkillParams skillParams) : AITool + { + public BetaSkillParams SkillParams => skillParams; + + public override string Name => SkillParams.SkillID; + + public override object? GetService(System.Type serviceType, object? serviceKey = null) => + serviceKey is null && serviceType?.IsInstanceOfType(skillParams) is true + ? skillParams + : base.GetService(serviceType!, serviceKey); + } } diff --git a/src/Anthropic/Services/Beta/Messages/BatchService.cs b/src/Anthropic/Services/Beta/Messages/BatchService.cs index 2289a676..d7fcdfd2 100644 --- a/src/Anthropic/Services/Beta/Messages/BatchService.cs +++ b/src/Anthropic/Services/Beta/Messages/BatchService.cs @@ -10,7 +10,7 @@ namespace Anthropic.Services.Beta.Messages; -/// +/// public sealed class BatchService : IBatchService { internal static void AddDefaultHeaders(HttpRequestMessage request) @@ -241,10 +241,13 @@ public async IAsyncEnumerable ResultsStreami using var response = await this ._client.Execute(request, cancellationToken) .ConfigureAwait(false); - await foreach (var message in SseMessage.GetEnumerable(response.Message, cancellationToken)) + await foreach ( + var betaMessageBatchIndividualResponse in Sse.Enumerate( + response.Message, + cancellationToken + ) + ) { - var betaMessageBatchIndividualResponse = - message.Deserialize(); if (this._client.ResponseValidation) { betaMessageBatchIndividualResponse.Validate(); diff --git a/src/Anthropic/Services/Beta/ModelService.cs b/src/Anthropic/Services/Beta/ModelService.cs index 989f3b37..ab7c7f8c 100644 --- a/src/Anthropic/Services/Beta/ModelService.cs +++ b/src/Anthropic/Services/Beta/ModelService.cs @@ -8,7 +8,7 @@ namespace Anthropic.Services.Beta; -/// +/// public sealed class ModelService : global::Anthropic.Services.Beta.IModelService { /// diff --git a/src/Anthropic/Services/Beta/SkillService.cs b/src/Anthropic/Services/Beta/SkillService.cs index 0c328d17..5c3405f0 100644 --- a/src/Anthropic/Services/Beta/SkillService.cs +++ b/src/Anthropic/Services/Beta/SkillService.cs @@ -9,7 +9,7 @@ namespace Anthropic.Services.Beta; -/// +/// public sealed class SkillService : ISkillService { internal static void AddDefaultHeaders(HttpRequestMessage request) diff --git a/src/Anthropic/Services/Beta/Skills/VersionService.cs b/src/Anthropic/Services/Beta/Skills/VersionService.cs index 68c0a24c..4917ccf5 100644 --- a/src/Anthropic/Services/Beta/Skills/VersionService.cs +++ b/src/Anthropic/Services/Beta/Skills/VersionService.cs @@ -8,7 +8,7 @@ namespace Anthropic.Services.Beta.Skills; -/// +/// public sealed class VersionService : IVersionService { internal static void AddDefaultHeaders(HttpRequestMessage request) diff --git a/src/Anthropic/Services/BetaService.cs b/src/Anthropic/Services/BetaService.cs index 853fa4e5..c2bc2b89 100644 --- a/src/Anthropic/Services/BetaService.cs +++ b/src/Anthropic/Services/BetaService.cs @@ -4,7 +4,7 @@ namespace Anthropic.Services; -/// +/// public sealed class BetaService : IBetaService { /// diff --git a/src/Anthropic/Services/MessageService.cs b/src/Anthropic/Services/MessageService.cs index 4de03608..db1af0a3 100644 --- a/src/Anthropic/Services/MessageService.cs +++ b/src/Anthropic/Services/MessageService.cs @@ -12,7 +12,7 @@ namespace Anthropic.Services; -/// +/// public sealed class MessageService : IMessageService { /// @@ -91,14 +91,15 @@ options with ) .Execute(request, cancellationToken) .ConfigureAwait(false); - await foreach (var message in SseMessage.GetEnumerable(response.Message, cancellationToken)) + await foreach ( + var message in Sse.Enumerate(response.Message, cancellationToken) + ) { - var deserializedMessage = message.Deserialize(); if (this._client.ResponseValidation) { - deserializedMessage.Validate(); + message.Validate(); } - yield return deserializedMessage; + yield return message; } } diff --git a/src/Anthropic/Services/Messages/BatchService.cs b/src/Anthropic/Services/Messages/BatchService.cs index fc8ce9b0..e8b936ad 100644 --- a/src/Anthropic/Services/Messages/BatchService.cs +++ b/src/Anthropic/Services/Messages/BatchService.cs @@ -10,7 +10,7 @@ namespace Anthropic.Services.Messages; -/// +/// public sealed class BatchService : IBatchService { /// @@ -236,10 +236,13 @@ public async IAsyncEnumerable ResultsStreaming( using var response = await this ._client.Execute(request, cancellationToken) .ConfigureAwait(false); - await foreach (var message in SseMessage.GetEnumerable(response.Message, cancellationToken)) + await foreach ( + var messageBatchIndividualResponse in Sse.Enumerate( + response.Message, + cancellationToken + ) + ) { - var messageBatchIndividualResponse = - message.Deserialize(); if (this._client.ResponseValidation) { messageBatchIndividualResponse.Validate(); diff --git a/src/Anthropic/Services/ModelService.cs b/src/Anthropic/Services/ModelService.cs index eeff2614..34158eb3 100644 --- a/src/Anthropic/Services/ModelService.cs +++ b/src/Anthropic/Services/ModelService.cs @@ -8,7 +8,7 @@ namespace Anthropic.Services; -/// +/// public sealed class ModelService : IModelService { ///