Skip to content

Commit

Permalink
Merge pull request #17 from BlazingRockStorm/dev
Browse files Browse the repository at this point in the history
version 0.1.0
  • Loading branch information
BlazingRockStorm authored Nov 22, 2024
2 parents c42a3f6 + 801f292 commit 052cd27
Show file tree
Hide file tree
Showing 15 changed files with 187 additions and 17 deletions.
5 changes: 5 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,8 @@
## [0.1.0] - 2024-11-22
All by [@BlazingRockStorm](https://github.com/BlazingRockStorm):
- Add `positive_check`
- Add Anthropic

## [0.0.5] - 2024-11-13
All by [@BlazingRockStorm](https://github.com/BlazingRockStorm):
- Rewrite the `analyze_sentence` method to have the output in form of Hash
Expand Down
7 changes: 6 additions & 1 deletion Gemfile.lock
Original file line number Diff line number Diff line change
@@ -1,13 +1,17 @@
PATH
remote: .
specs:
sentiment-ai (0.0.5)
sentiment-ai (0.1.0)

GEM
remote: https://rubygems.org/
specs:
addressable (2.8.7)
public_suffix (>= 2.0.2, < 7.0)
anthropic (0.3.2)
event_stream_parser (>= 0.3.0, < 2.0.0)
faraday (>= 1)
faraday-multipart (>= 1)
base64 (0.2.0)
bigdecimal (3.1.8)
concurrent-ruby (1.3.4)
Expand Down Expand Up @@ -98,6 +102,7 @@ PLATFORMS
x86_64-darwin-22

DEPENDENCIES
anthropic (~> 0.3.2)
csv (~> 3.3)
dotenv
gemini-ai (~> 4.2)
Expand Down
13 changes: 10 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ require "sentiment_ai"
Then use it like this:

```ruby
sentiment = SentimentAI.new(YOUR_MODEL,YOUR_API_KEY)
sentiment = SentimentAI.new(YOUR_PROVIDER,YOUR_API_KEY)
```

For example:
Expand All @@ -38,7 +38,7 @@ sentiment = SentimentAI.new(:open_ai, OPEN_AI_KEY)

For the current version, the gem supports only OpenAI and Google Gemini.

After calling the model, use:
After calling the provider, use:
```ruby
sentiment.analyze_sentence("I Love Ruby")
# => { :sentence => "I Love Ruby", :sentiment => "positive" }
Expand Down Expand Up @@ -71,12 +71,19 @@ sentiment = SentimentAI.new(:open_ai, OPEN_AI_KEY, :ja)
sentiment.analyze_sentence("Rubyは世界一プログラミング言語")
# => { :sentence => "Rubyは世界一プログラミング言語", :sentiment => "肯定的" }
```
### Supported GenAI models
If you want to only choose positive, use:
```ruby
sentiment.positive_check("I Love Ruby")
# => { :sentence => "I Love Ruby", :positive => true }
# => { :sentence => "It was never love for me", :positive => false }
```
### Supported GenAI providers

| Language | Code |
|----------|------|
| OpenAI(GPT) | `:open_ai` |
| Google Gemini | `:gemini_ai_pro` |
| Anthropic | `:anthropic` |

### Supported languages

Expand Down
3 changes: 2 additions & 1 deletion config/locales/en.yml
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
en:
prompt:
sentence: "Analyze the sentiment of the sentence given below.\n%{sentence}\nThe output should be in the format- value"
sentence: "Analyze the sentiment of the sentence given below.\n%{sentence}\nThe output should be in the format- value"
positive_check: "Is the sentence given below positive?\n%{sentence}\nThe output should be true or false"
3 changes: 2 additions & 1 deletion config/locales/ja.yml
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
ja:
prompt:
sentence: "テキストを「中立」、「否定的」、または「肯定的」に分類してください。 テキスト:%{sentence}\n結果の形式- 値"
sentence: "テキストを「中立」、「否定的」、または「肯定的」に分類してください。 テキスト:%{sentence}\n結果の形式- 値"
positive_check: "テキストは肯定的ですか?\n%{sentence}\n「はい」はtrue、 「いいえ」は false"
3 changes: 2 additions & 1 deletion config/locales/vi.yml
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
vi:
prompt:
sentence: "Phân tích sắc thái của câu dưới đây là tích cực, tiêu cực hay trung lập.\n%{sentence}\nKết quả trả về dưới dạng- Gía trị"
sentence: "Phân tích sắc thái của câu dưới đây là tích cực, tiêu cực hay trung lập.\n%{sentence}\nKết quả trả về dưới dạng- Gía trị"
positive_check: "Câu sau đây có tích cực hay không?\n%{sentence}\nkết quả trả về là true hoặc false"
12 changes: 10 additions & 2 deletions lib/sentiment_ai.rb
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
require 'sentiment_ai/version'
require 'sentiment_ai/core/gemini_driver'
require 'sentiment_ai/core/openai_driver'
require 'sentiment_ai/core/anthropic_driver'
require 'i18n'
require 'csv'

Expand All @@ -19,13 +20,15 @@ def self.new(*args)
end

class Base
def initialize(model, api_key, language = :en)
def initialize(provider, api_key, language = :en)
I18n.locale = language
@generative_ai = case model
@generative_ai = case provider
when :open_ai
Core::OpenAIDriver.new(api_key)
when :gemini_ai_pro
Core::GeminiDriver.new(api_key)
when :anthropic
Core::AnthropicDriver.new(api_key)
else
raise ArgumentError
end
Expand All @@ -36,6 +39,11 @@ def analyze_sentence(sentence)
{ sentence: sentence, sentiment: sentiment }
end

def positive_check(sentence)
sentiment_bool = @generative_ai.positive_check(sentence)
{ sentence: sentence, positive: sentiment_bool == 'true' }
end

def analyze_array(array)
array.map { |sentence| analyze_sentence(sentence) }
end
Expand Down
41 changes: 41 additions & 0 deletions lib/sentiment_ai/core/anthropic_driver.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
# frozen_string_literal: true

require 'anthropic'

module SentimentAI
module Core
class AnthropicDriver
def initialize(api_key)
@sentiment_ai = Anthropic::Client.new(access_token: api_key)
end

def analyze_sentence(sentence)
text_request = I18n.t('prompt.sentence', sentence: sentence)

@sentiment_ai.messages(
parameters: {
model: 'claude-3-haiku-20240307',
messages: [
{ 'role': 'user', 'content': text_request }
],
max_tokens: 1000
}
)
end

def positive_check(sentence)
text_request = I18n.t('prompt.positive_check', sentence: sentence)

@sentiment_ai.messages(
parameters: {
model: 'claude-3-haiku-20240307',
messages: [
{ 'role': 'user', 'content': text_request }
],
max_tokens: 1000
}
)
end
end
end
end
10 changes: 10 additions & 0 deletions lib/sentiment_ai/core/gemini_driver.rb
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,16 @@ def analyze_sentence(sentence)
extract_candidates(response)
end

def positive_check(sentence)
text_request = I18n.t('prompt.positive_check', sentence: sentence)

response = @sentiment_ai.stream_generate_content({
contents: { role: 'user', parts: { text: text_request } },
generationConfig: { temperature: 0 }
})
extract_candidates(response)
end

private

def extract_candidates(candidates)
Expand Down
15 changes: 15 additions & 0 deletions lib/sentiment_ai/core/openai_driver.rb
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,21 @@ def analyze_sentence(sentence)
}
)
end

def positive_check(sentence)
text_request = I18n.t('prompt.positive_check', sentence: sentence)

@sentiment_ai.chat(
parameters: {
model: 'gpt-4o',
messages: [{ role: 'user', content: text_request }],
temperature: 0.7,
stream: proc do |chunk, _bytesize|
print chunk.dig('choices', 0, 'delta', 'content')
end
}
)
end
end
end
end
2 changes: 1 addition & 1 deletion lib/sentiment_ai/version.rb
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
# frozen_string_literal: true

module SentimentAI
VERSION = '0.0.5'
VERSION = '0.1.0'
end
1 change: 1 addition & 0 deletions sentiment-ai.gemspec
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ Gem::Specification.new do |spec|
spec.add_development_dependency 'csv', '~> 3.3'
spec.add_development_dependency 'i18n', '~> 1.14'

spec.add_development_dependency 'anthropic', '~> 0.3.2'
spec.add_development_dependency 'gemini-ai', '~> 4.2'
spec.add_development_dependency 'ruby-openai', '~> 6.0'
end
59 changes: 59 additions & 0 deletions spec/ai_models/anthropic_spec.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
# frozen_string_literal: true

require 'spec_helper'
require 'dotenv/load'

RSpec.describe 'Using Anthropic provider' do
let(:sentiment) { SentimentAI.new(:anthropic, ENV['ANTHROPIC_KEY']) }
let(:japanese_sentiment) { SentimentAI.new(:anthropic, ENV['ANTHROPIC_KEY'], :ja) }

describe 'new provider behaviours' do
it 'provider being called correctly' do
expect(sentiment).to be_truthy
end
end

# describe 'analyze sentence in another language' do
# describe '#analyze_sentence' do
# it 'return the sentiment of the sentence' do
# expect(japanese_sentiment.analyze_sentence('うまい!')).to eq({ sentence: 'うまい!', sentiment: '肯定的' })
# expect(japanese_sentiment.analyze_sentence('不愉快')).to eq({ sentence: '不愉快', sentiment: '否定的' })
# expect(japanese_sentiment.analyze_sentence('休暇はまずまずでした。')).to eq({ sentence: '休暇はまずまずでした。', sentiment: '中立' })
# end
# end
# end

describe 'analyze feature' do
describe '#analyze_sentence' do
it 'return the sentiment of the sentence' do
expect(sentiment.analyze_sentence('Delicious food')).to eq({ sentence: 'Delicious food',
sentiment: 'positive' })
expect(sentiment.analyze_sentence('Too noisy!!!')).to eq({ sentence: 'Too noisy!!!', sentiment: 'negative' })
expect(sentiment.analyze_sentence("I really don't know how to feel about Pokemon")).to eq({
sentence: "I really don't know how to feel about Pokemon", sentiment: 'neutral'
})
end
end

describe '#positive_check' do
it 'return true or false' do
expect(sentiment.positive_check('Delicious food')).to eq({ sentence: 'Delicious food',
positive: true })
expect(sentiment.positive_check('Too noisy!!!')).to eq({ sentence: 'Too noisy!!!', positive: false })
end
end

describe '#analyze_array' do
let(:array) { ['Delicious food', 'Too noisy!!!', "I really don't know how to feel about Pokemon"] }
let(:result_array) do
[{ sentence: 'Delicious food', sentiment: 'positive' },
{ sentence: 'Too noisy!!!', sentiment: 'negative' },
{ sentence: "I really don't know how to feel about Pokemon", sentiment: 'neutral' }]
end

it 'return the sentiments of all sentences in the array' do
expect(sentiment.analyze_array(array)).to eq(result_array)
end
end
end
end
14 changes: 11 additions & 3 deletions spec/ai_models/gemini_pro_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,12 @@
require 'spec_helper'
require 'dotenv/load'

RSpec.describe 'Using Gemini Pro model' do
RSpec.describe 'Using Gemini Pro provider' do
let(:sentiment) { SentimentAI.new(:gemini_ai_pro, ENV['GEMINI_API']) }
let(:japanese_sentiment) { SentimentAI.new(:gemini_ai_pro, ENV['GEMINI_API'], :ja) }

describe 'new model behaviours' do
it 'model being called correctly' do
describe 'new provider behaviours' do
it 'provider being called correctly' do
expect(sentiment).to be_truthy
end
end
Expand All @@ -35,6 +35,14 @@
end
end

describe '#positive_check' do
it 'return true or false' do
expect(sentiment.positive_check('Delicious food')).to eq({ sentence: 'Delicious food',
positive: true })
expect(sentiment.positive_check('Too noisy!!!')).to eq({ sentence: 'Too noisy!!!', positive: false })
end
end

describe '#analyze_array' do
let(:array) { ['Delicious food', 'Too noisy!!!', "I really don't know how to feel about Pokemon"] }
let(:result_array) do
Expand Down
16 changes: 12 additions & 4 deletions spec/ai_models/openai_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,12 @@
require 'spec_helper'
require 'dotenv/load'

RSpec.describe 'Using OpenAI model' do
RSpec.describe 'Using OpenAI provider' do
let(:sentiment) { SentimentAI.new(:open_ai, ENV['OPENAI_KEY']) }
let(:japanese_sentiment) { SentimentAI.new(:gemini_ai_pro, ENV['OPENAI_KEY'], :ja) }
let(:japanese_sentiment) { SentimentAI.new(:open_ai, ENV['OPENAI_KEY'], :ja) }

describe 'new model behaviours' do
it 'model being called correctly' do
describe 'new provider behaviours' do
it 'provider being called correctly' do
expect(sentiment).to be_truthy
end
end
Expand All @@ -35,6 +35,14 @@
end
end

describe '#positive_check' do
it 'return true or false' do
expect(sentiment.positive_check('Delicious food')).to eq({ sentence: 'Delicious food',
positive: true })
expect(sentiment.positive_check('Too noisy!!!')).to eq({ sentence: 'Too noisy!!!', positive: false })
end
end

describe '#analyze_array' do
let(:array) { ['Delicious food', 'Too noisy!!!', "I really don't know how to feel about Pokemon"] }
let(:result_array) do
Expand Down

0 comments on commit 052cd27

Please sign in to comment.