From 42231378b8a73baabe90b613b27c46f526b01ee9 Mon Sep 17 00:00:00 2001 From: Dick Davis Date: Sat, 20 Apr 2024 13:05:50 -0500 Subject: [PATCH] Add support for tools beta (#19) * Implement support for tools * Update documentation --- .reek.yml | 3 +++ CHANGELOG.md | 13 +++++++++++- Gemfile.lock | 2 +- README.md | 33 ++++++++++++++++++++++++++--- lib/anthropic/messages.rb | 16 +++++++++++++- lib/anthropic/version.rb | 2 +- spec/lib/anthropic/messages_spec.rb | 17 ++++++++++++++- 7 files changed, 78 insertions(+), 8 deletions(-) diff --git a/.reek.yml b/.reek.yml index 7e2b45f..4163b13 100644 --- a/.reek.yml +++ b/.reek.yml @@ -8,3 +8,6 @@ detectors: BooleanParameter: exclude: - 'Anthropic::Messages#initialize' + DuplicateMethodCall: + exclude: + - 'Anthropic::Messages#create' diff --git a/CHANGELOG.md b/CHANGELOG.md index 6816cee..36a2312 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,16 @@ ## [Unreleased] +## [0.4.0] - 2024-04-20 + +### Added + +- Add support for the tools beta. + +### Updated + +- Remove beta header for Messages API as the API is no longer in beta. + ## [0.3.0] - 2023-12-28 ### Added @@ -47,7 +57,8 @@ - Initial release -[Unreleased]: https://github.com/dickdavis/anthropic-rb/compare/v0.3.0...HEAD +[Unreleased]: https://github.com/dickdavis/anthropic-rb/compare/v0.4.0...HEAD +[0.4.0]: https://github.com/dickdavis/anthropic-rb/compare/v0.3.0...v0.4.0 [0.3.0]: https://github.com/dickdavis/anthropic-rb/compare/v0.2.5...v0.3.0 [0.2.5]: https://github.com/dickdavis/anthropic-rb/compare/v0.2.3...v0.2.5 [0.2.3]: https://github.com/dickdavis/anthropic-rb/compare/v0.2.2...v0.2.3 diff --git a/Gemfile.lock b/Gemfile.lock index 4d86d68..c87d24a 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -1,7 +1,7 @@ PATH remote: . specs: - anthropic-rb (0.3.0) + anthropic-rb (0.4.0) httpx (>= 1.1.5) json-schema (>= 4.1.1) diff --git a/README.md b/README.md index 694d7d9..a9fe1e2 100644 --- a/README.md +++ b/README.md @@ -28,10 +28,10 @@ end ### Messages API -You can send a request to the Messages API. The Messages API is currently in beta; as such, you'll need to pass the `beta` flag when calling the API to ensure the correct header is included. +You can send a request to the Messages API. ```ruby -Anthropic.messages(beta: true).create(model: 'claude-2.1', max_tokens: 200, messages: [{role: 'user', content: 'Yo what up?'}]) +Anthropic.messages.create(model: 'claude-2.1', max_tokens: 200, messages: [{role: 'user', content: 'Yo what up?'}]) # Output => # { @@ -48,7 +48,7 @@ Anthropic.messages(beta: true).create(model: 'claude-2.1', max_tokens: 200, mess Alternatively, you can stream the response: ```ruby -Anthropic.messages(beta: true).create(model: 'claude-2.1', max_tokens: 200, messages: [{role: 'user', content: 'Yo what up?'}], stream: true) do |event| +Anthropic.messages.create(model: 'claude-2.1', max_tokens: 200, messages: [{role: 'user', content: 'Yo what up?'}], stream: true) do |event| puts event end @@ -62,6 +62,33 @@ end # { type: 'message_stop' } ``` +You can also experiment with the new tools beta by passing the `beta` flag when calling the API. This will ensure each request includes the correct beta header. + +```ruby +tools = [ + { + name: 'get_weather', + description: 'Get the current weather in a given location', + input_schema: { + type: 'object', + properties: { + location: { type: 'string' } + }, + required: ['location'] + } + } +] + +Anthropic.messages(beta: true).create( + model: 'claude-3-opus-20240229', + max_tokens: 200, + tools:, + messages: [{role: 'user', content: 'What is the weather like in Nashville?'}] +) +``` + +Streaming is currently not supported by the tools beta. You can find out more information about tools in the [documentation](https://docs.anthropic.com/claude/docs/tool-use). + ### Completions API To make a request to the Completions API: diff --git a/lib/anthropic/messages.rb b/lib/anthropic/messages.rb index fe013d1..3fcef5f 100644 --- a/lib/anthropic/messages.rb +++ b/lib/anthropic/messages.rb @@ -7,6 +7,9 @@ class Messages # Error for when the API version is not supported. class UnsupportedApiVersionError < StandardError; end + # Error for when a beta feature is not used correctly + class UnsupportedBetaOptionError < StandardError; end + ENDPOINT = 'https://api.anthropic.com/v1/messages' V1_SCHEMA = { type: 'object', @@ -18,6 +21,14 @@ class UnsupportedApiVersionError < StandardError; end system: { type: 'string' }, stop_sequences: { type: 'array', items: { type: 'string' } }, temperature: { type: 'number' }, + tools: { + type: 'array', + items: { + name: { type: 'string' }, + description: { type: 'string' }, + input_schema: { type: 'object' } + } + }, top_k: { type: 'integer' }, top_p: { type: 'number' }, metadata: { type: 'object' }, @@ -31,7 +42,10 @@ def initialize(beta: false) end def create(**params, &) + raise UnsupportedBetaOptionError, 'Tool use is not yet supported in streaming mode' if params[:stream] && beta + JSON::Validator.validate!(schema_for_api_version, params) + return Anthropic::Client.post(ENDPOINT, params, additional_headers) unless params[:stream] Anthropic::Client.post_as_stream(ENDPOINT, params, additional_headers, &) @@ -56,7 +70,7 @@ def schema_for_api_version def additional_headers return {} unless beta - { 'anthropic-beta' => 'messages-2023-12-15' } + { 'anthropic-beta' => 'tools-2024-04-04' } end end end diff --git a/lib/anthropic/version.rb b/lib/anthropic/version.rb index 2976ada..eded74c 100644 --- a/lib/anthropic/version.rb +++ b/lib/anthropic/version.rb @@ -1,5 +1,5 @@ # frozen_string_literal: true module Anthropic - VERSION = '0.3.0' + VERSION = '0.4.0' end diff --git a/spec/lib/anthropic/messages_spec.rb b/spec/lib/anthropic/messages_spec.rb index 78c5a1d..3a3edd9 100644 --- a/spec/lib/anthropic/messages_spec.rb +++ b/spec/lib/anthropic/messages_spec.rb @@ -30,7 +30,22 @@ call_method expect(WebMock) .to have_requested(:post, 'https://api.anthropic.com/v1/messages') - .with(headers: { 'anthropic-beta' => 'messages-2023-12-15' }) + .with(headers: { 'anthropic-beta' => 'tools-2024-04-04' }) + end + + context 'when the request is for streaming' do # rubocop:disable RSpec/NestedGroups + let(:params) do + { + model: 'claude-2.1', + messages: [{ role: 'user', content: 'foo' }], + max_tokens: 200, + stream: true + } + end + + it 'raises an error' do + expect { call_method }.to raise_error(Anthropic::Messages::UnsupportedBetaOptionError) + end end end