llm_conductor 1.5.0 → 1.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.rubocop.yml +10 -1
- data/docs/custom-parameters.md +39 -2
- data/examples/gemini_usage.rb +83 -11
- data/lib/llm_conductor/client_factory.rb +2 -0
- data/lib/llm_conductor/clients/gemini_client.rb +54 -5
- data/lib/llm_conductor/configuration.rb +27 -5
- data/lib/llm_conductor/patches/gemini_vertex_api_key.rb +52 -0
- data/lib/llm_conductor/version.rb +1 -1
- data/lib/llm_conductor.rb +0 -2
- metadata +3 -2
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: a132b52551949cd8cd7446e2cf9a26f1dacba997dbae0965494b4ee174cf5905
|
|
4
|
+
data.tar.gz: 89d87446edea2d31c7194f84e1c98cbb11d241a0a1cd57b2878b387c94b441a5
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 21204a00bc9d437fa702dc67f6224c8ef325e32daa94b252421fdff430929a03ca9903634df739b72d11f4b689320d7bfb1b626e800443aa90d0393ab5d11b01
|
|
7
|
+
data.tar.gz: 490ded3cf0e013a0edaed1bb66b4c91750a6503419c37e58b8fd4e5d53db464ff0785a4de4a76c8b3b87b787684fa327d78a7c8c872dc30608a0225de829c59d
|
data/.rubocop.yml
CHANGED
|
@@ -30,7 +30,7 @@ Lint/ConstantDefinitionInBlock:
|
|
|
30
30
|
Enabled: false
|
|
31
31
|
|
|
32
32
|
Metrics/ClassLength:
|
|
33
|
-
Max:
|
|
33
|
+
Max: 125
|
|
34
34
|
|
|
35
35
|
Metrics/MethodLength:
|
|
36
36
|
Max: 15
|
|
@@ -38,6 +38,8 @@ Metrics/MethodLength:
|
|
|
38
38
|
- 'lib/llm_conductor/prompts.rb'
|
|
39
39
|
- 'lib/llm_conductor/clients/openrouter_client.rb'
|
|
40
40
|
- 'lib/llm_conductor/clients/zai_client.rb'
|
|
41
|
+
- 'lib/llm_conductor/client_factory.rb'
|
|
42
|
+
- 'examples/*.rb'
|
|
41
43
|
|
|
42
44
|
RSpec/ExampleLength:
|
|
43
45
|
Enabled: false
|
|
@@ -96,6 +98,12 @@ Metrics/AbcSize:
|
|
|
96
98
|
- 'lib/llm_conductor/prompts.rb'
|
|
97
99
|
- 'lib/llm_conductor/clients/openrouter_client.rb'
|
|
98
100
|
- 'lib/llm_conductor/clients/zai_client.rb'
|
|
101
|
+
- 'examples/*.rb'
|
|
102
|
+
|
|
103
|
+
Metrics/ParameterLists:
|
|
104
|
+
Exclude:
|
|
105
|
+
- 'lib/llm_conductor.rb'
|
|
106
|
+
- 'lib/llm_conductor/configuration.rb'
|
|
99
107
|
|
|
100
108
|
Metrics/CyclomaticComplexity:
|
|
101
109
|
Exclude:
|
|
@@ -103,6 +111,7 @@ Metrics/CyclomaticComplexity:
|
|
|
103
111
|
- 'lib/llm_conductor/prompts.rb'
|
|
104
112
|
- 'lib/llm_conductor/clients/openrouter_client.rb'
|
|
105
113
|
- 'lib/llm_conductor/clients/zai_client.rb'
|
|
114
|
+
- 'examples/*.rb'
|
|
106
115
|
|
|
107
116
|
Metrics/PerceivedComplexity:
|
|
108
117
|
Exclude:
|
data/docs/custom-parameters.md
CHANGED
|
@@ -29,7 +29,8 @@ params: { temperature: 0.3, top_p: 0.85 }
|
|
|
29
29
|
| Provider | Status |
|
|
30
30
|
|----------|--------|
|
|
31
31
|
| Ollama | ✅ Supported |
|
|
32
|
-
|
|
|
32
|
+
| Gemini | ✅ Supported |
|
|
33
|
+
| OpenAI, Anthropic, etc. | 🔜 Coming soon |
|
|
33
34
|
|
|
34
35
|
---
|
|
35
36
|
|
|
@@ -133,6 +134,42 @@ response = LlmConductor.generate(
|
|
|
133
134
|
)
|
|
134
135
|
```
|
|
135
136
|
|
|
137
|
+
## Gemini Parameters Reference
|
|
138
|
+
|
|
139
|
+
Below are common parameters supported by Google Gemini via `generationConfig`. For a complete list, see the [Gemini API docs](https://ai.google.dev/gemini-api/docs/text-generation).
|
|
140
|
+
|
|
141
|
+
### Supported Parameters
|
|
142
|
+
|
|
143
|
+
| Ruby Key | Gemini API Key | Type | Description |
|
|
144
|
+
|----------|---------------|------|-------------|
|
|
145
|
+
| `temperature` | `temperature` | Float | Controls randomness (0.0-2.0) |
|
|
146
|
+
| `top_p` | `topP` | Float | Nucleus sampling threshold (0.0-1.0) |
|
|
147
|
+
| `top_k` | `topK` | Integer | Top-k sampling limit |
|
|
148
|
+
| `max_tokens` | `maxOutputTokens` | Integer | Maximum tokens to generate |
|
|
149
|
+
| `max_output_tokens` | `maxOutputTokens` | Integer | Alias for max_tokens |
|
|
150
|
+
| `candidate_count` | `candidateCount` | Integer | Number of candidates to return |
|
|
151
|
+
| `stop_sequences` | `stopSequences` | Array | Stop sequences that end generation |
|
|
152
|
+
|
|
153
|
+
### Gemini Usage Examples
|
|
154
|
+
|
|
155
|
+
```ruby
|
|
156
|
+
# Low temperature for focused output
|
|
157
|
+
response = LlmConductor.generate(
|
|
158
|
+
model: 'gemini-2.5-flash',
|
|
159
|
+
prompt: 'Summarize this article.',
|
|
160
|
+
vendor: :gemini,
|
|
161
|
+
params: { temperature: 0.3, max_tokens: 500 }
|
|
162
|
+
)
|
|
163
|
+
|
|
164
|
+
# Creative writing with Gemini
|
|
165
|
+
response = LlmConductor.generate(
|
|
166
|
+
model: 'gemini-2.5-flash',
|
|
167
|
+
prompt: 'Write a poem about the ocean.',
|
|
168
|
+
vendor: :gemini,
|
|
169
|
+
params: { temperature: 0.9, top_p: 0.95, top_k: 40 }
|
|
170
|
+
)
|
|
171
|
+
```
|
|
172
|
+
|
|
136
173
|
## Ollama Parameters Reference
|
|
137
174
|
|
|
138
175
|
Below are common parameters supported by Ollama. For a complete list, see the [Ollama documentation](https://github.com/ollama/ollama/blob/main/docs/modelfile.md#valid-parameters-and-values).
|
|
@@ -311,11 +348,11 @@ Always refer to your provider's documentation for supported parameters.
|
|
|
311
348
|
|
|
312
349
|
Currently, custom parameters are fully supported for:
|
|
313
350
|
- ✅ **Ollama**
|
|
351
|
+
- ✅ **Google (Gemini)** — maps snake_case Ruby keys to camelCase `generationConfig`
|
|
314
352
|
|
|
315
353
|
Coming soon:
|
|
316
354
|
- 🔜 OpenAI (GPT)
|
|
317
355
|
- 🔜 Anthropic (Claude)
|
|
318
|
-
- 🔜 Google (Gemini)
|
|
319
356
|
- 🔜 Groq
|
|
320
357
|
- 🔜 OpenRouter
|
|
321
358
|
- 🔜 Z.ai
|
data/examples/gemini_usage.rb
CHANGED
|
@@ -1,18 +1,90 @@
|
|
|
1
|
+
#!/usr/bin/env ruby
|
|
1
2
|
# frozen_string_literal: true
|
|
2
3
|
|
|
4
|
+
# Connectivity test for all Gemini auth methods.
|
|
5
|
+
# Omit SCENARIO to run all scenarios that have the required env vars set.
|
|
6
|
+
#
|
|
7
|
+
# Scenario A — Generative Language API (api_key)
|
|
8
|
+
# SCENARIO=api_key GEMINI_API_KEY=... ruby examples/gemini_usage.rb
|
|
9
|
+
#
|
|
10
|
+
# Scenario B — Vertex AI with account-bound API key
|
|
11
|
+
# SCENARIO=vertex_api_key GEMINI_API_KEY=... GOOGLE_VERTEX_PROJECT_ID=... ruby examples/gemini_usage.rb
|
|
12
|
+
#
|
|
13
|
+
# Scenario C — Vertex AI via Application Default Credentials
|
|
14
|
+
# SCENARIO=adc \
|
|
15
|
+
# GOOGLE_VERTEX_PROJECT_ID=... \
|
|
16
|
+
# GOOGLE_APPLICATION_CREDENTIALS=/path/to/sa.json \
|
|
17
|
+
# ruby examples/gemini_usage.rb
|
|
18
|
+
#
|
|
19
|
+
# Scenario C — Vertex AI via credentials file contents
|
|
20
|
+
# SCENARIO=file_contents \
|
|
21
|
+
# GOOGLE_VERTEX_PROJECT_ID=... \
|
|
22
|
+
# GOOGLE_CREDENTIALS_FILE_CONTENTS=$(cat /path/to/sa.json) \
|
|
23
|
+
# ruby examples/gemini_usage.rb
|
|
24
|
+
|
|
3
25
|
require_relative '../lib/llm_conductor'
|
|
4
26
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
27
|
+
MODEL = 'gemini-2.5-flash'
|
|
28
|
+
PROMPT = 'Say hello.'
|
|
29
|
+
|
|
30
|
+
SCENARIOS = {
|
|
31
|
+
'api_key' => -> { ENV['GEMINI_API_KEY'] && !ENV['GOOGLE_VERTEX_PROJECT_ID'] },
|
|
32
|
+
'vertex_api_key' => -> { ENV['GEMINI_API_KEY'] && ENV['GOOGLE_VERTEX_PROJECT_ID'] },
|
|
33
|
+
'adc' => -> { ENV['GOOGLE_VERTEX_PROJECT_ID'] && ENV['GOOGLE_APPLICATION_CREDENTIALS'] },
|
|
34
|
+
'file_contents' => -> { ENV['GOOGLE_VERTEX_PROJECT_ID'] && ENV['GOOGLE_CREDENTIALS_FILE_CONTENTS'] }
|
|
35
|
+
}.freeze
|
|
36
|
+
|
|
37
|
+
def run_scenario(name)
|
|
38
|
+
case name
|
|
39
|
+
when 'api_key'
|
|
40
|
+
LlmConductor.configure { |c| c.gemini(api_key: ENV.fetch('GEMINI_API_KEY')) }
|
|
41
|
+
label = 'api_key'
|
|
42
|
+
|
|
43
|
+
when 'vertex_api_key'
|
|
44
|
+
LlmConductor.configure do |c|
|
|
45
|
+
c.gemini(api_key: ENV.fetch('GEMINI_API_KEY'),
|
|
46
|
+
project_id: ENV.fetch('GOOGLE_VERTEX_PROJECT_ID'),
|
|
47
|
+
region: ENV['GOOGLE_VERTEX_REGION'])
|
|
48
|
+
end
|
|
49
|
+
label = 'vertex_ai/api_key'
|
|
50
|
+
|
|
51
|
+
when 'adc'
|
|
52
|
+
LlmConductor.configure do |c|
|
|
53
|
+
c.gemini(project_id: ENV.fetch('GOOGLE_VERTEX_PROJECT_ID'),
|
|
54
|
+
region: ENV['GOOGLE_VERTEX_REGION'])
|
|
55
|
+
end
|
|
56
|
+
label = 'vertex_ai/adc'
|
|
57
|
+
|
|
58
|
+
when 'file_contents'
|
|
59
|
+
LlmConductor.configure do |c|
|
|
60
|
+
c.gemini(project_id: ENV.fetch('GOOGLE_VERTEX_PROJECT_ID'),
|
|
61
|
+
region: ENV['GOOGLE_VERTEX_REGION'],
|
|
62
|
+
file_contents: ENV.fetch('GOOGLE_CREDENTIALS_FILE_CONTENTS'))
|
|
63
|
+
end
|
|
64
|
+
label = 'vertex_ai/file_contents'
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
response = LlmConductor.generate(model: MODEL, prompt: PROMPT)
|
|
68
|
+
raise 'Empty response' if response.output.nil? || response.output.strip.empty?
|
|
69
|
+
|
|
70
|
+
puts "[#{label}] OK — #{response.output.strip}"
|
|
71
|
+
rescue StandardError => e
|
|
72
|
+
puts "[#{label}] FAILED — #{e.message}"
|
|
73
|
+
false
|
|
8
74
|
end
|
|
9
75
|
|
|
10
|
-
|
|
11
|
-
response = LlmConductor.generate(
|
|
12
|
-
model: 'gemini-2.5-flash',
|
|
13
|
-
prompt: 'Explain how AI works in a few words'
|
|
14
|
-
)
|
|
76
|
+
scenario = ENV['SCENARIO']
|
|
15
77
|
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
78
|
+
if scenario
|
|
79
|
+
abort "Unknown SCENARIO=#{scenario}. Use: api_key | vertex_api_key | adc | file_contents" unless SCENARIOS.key?(scenario)
|
|
80
|
+
run_scenario(scenario)
|
|
81
|
+
else
|
|
82
|
+
ran = 0
|
|
83
|
+
SCENARIOS.each do |name, available|
|
|
84
|
+
next unless available.call
|
|
85
|
+
|
|
86
|
+
run_scenario(name)
|
|
87
|
+
ran += 1
|
|
88
|
+
end
|
|
89
|
+
puts '(no scenarios ran — set the required env vars)' if ran.zero?
|
|
90
|
+
end
|
|
@@ -5,6 +5,7 @@ require 'base64'
|
|
|
5
5
|
require 'net/http'
|
|
6
6
|
require 'uri'
|
|
7
7
|
require_relative 'concerns/vision_support'
|
|
8
|
+
require_relative '../patches/gemini_vertex_api_key'
|
|
8
9
|
|
|
9
10
|
module LlmConductor
|
|
10
11
|
module Clients
|
|
@@ -15,20 +16,49 @@ module LlmConductor
|
|
|
15
16
|
|
|
16
17
|
private
|
|
17
18
|
|
|
19
|
+
# Gemini REST API uses camelCase keys in generationConfig.
|
|
20
|
+
PARAM_KEY_MAP = {
|
|
21
|
+
temperature: :temperature,
|
|
22
|
+
top_p: :topP,
|
|
23
|
+
top_k: :topK,
|
|
24
|
+
max_tokens: :maxOutputTokens,
|
|
25
|
+
max_output_tokens: :maxOutputTokens,
|
|
26
|
+
candidate_count: :candidateCount,
|
|
27
|
+
stop_sequences: :stopSequences
|
|
28
|
+
}.freeze
|
|
29
|
+
|
|
18
30
|
def generate_content(prompt)
|
|
19
31
|
content = format_content(prompt)
|
|
20
32
|
parts = build_parts_for_gemini(content)
|
|
21
33
|
|
|
22
34
|
payload = {
|
|
23
35
|
contents: [
|
|
24
|
-
{ parts: }
|
|
36
|
+
{ role: 'user', parts: }
|
|
25
37
|
]
|
|
26
38
|
}
|
|
27
39
|
|
|
40
|
+
# Inject generationConfig from params when present
|
|
41
|
+
generation_config = build_generation_config
|
|
42
|
+
payload[:generationConfig] = generation_config if generation_config
|
|
43
|
+
|
|
28
44
|
response = client.generate_content(payload)
|
|
29
45
|
response.dig('candidates', 0, 'content', 'parts', 0, 'text')
|
|
30
46
|
end
|
|
31
47
|
|
|
48
|
+
# Build Gemini generationConfig from params hash.
|
|
49
|
+
# Maps snake_case Ruby keys to camelCase Gemini API keys.
|
|
50
|
+
# @return [Hash, nil] generationConfig hash or nil if no mapped params
|
|
51
|
+
def build_generation_config
|
|
52
|
+
return unless params.is_a?(Hash) && params.any?
|
|
53
|
+
|
|
54
|
+
gen_cfg = {}
|
|
55
|
+
params.each do |key, value|
|
|
56
|
+
mapped = PARAM_KEY_MAP[key.to_sym]
|
|
57
|
+
gen_cfg[mapped] = value if mapped
|
|
58
|
+
end
|
|
59
|
+
gen_cfg.any? ? gen_cfg : nil
|
|
60
|
+
end
|
|
61
|
+
|
|
32
62
|
# Build parts array for Gemini API from formatted content
|
|
33
63
|
# Converts VisionSupport format to Gemini's specific format
|
|
34
64
|
# @param content [String, Array] Formatted content from VisionSupport
|
|
@@ -127,14 +157,33 @@ module LlmConductor
|
|
|
127
157
|
@client ||= begin
|
|
128
158
|
config = LlmConductor.configuration.provider_config(:gemini)
|
|
129
159
|
Gemini.new(
|
|
130
|
-
credentials:
|
|
131
|
-
service: 'generative-language-api',
|
|
132
|
-
api_key: config[:api_key]
|
|
133
|
-
},
|
|
160
|
+
credentials: build_credentials(config),
|
|
134
161
|
options: { model: }
|
|
135
162
|
)
|
|
136
163
|
end
|
|
137
164
|
end
|
|
165
|
+
|
|
166
|
+
def build_credentials(config)
|
|
167
|
+
if config[:project_id] && config[:api_key]
|
|
168
|
+
{ service: 'vertex-ai-api', region: config[:region], project_id: config[:project_id],
|
|
169
|
+
api_key: config[:api_key] }
|
|
170
|
+
elsif config[:project_id]
|
|
171
|
+
vertex_ai_credentials(config)
|
|
172
|
+
else
|
|
173
|
+
{ service: 'generative-language-api', api_key: config[:api_key] }
|
|
174
|
+
end
|
|
175
|
+
end
|
|
176
|
+
|
|
177
|
+
def vertex_ai_credentials(config)
|
|
178
|
+
creds = {
|
|
179
|
+
service: 'vertex-ai-api',
|
|
180
|
+
region: config[:region],
|
|
181
|
+
project_id: config[:project_id]
|
|
182
|
+
}
|
|
183
|
+
creds[:file_path] = config[:file_path] if config[:file_path]
|
|
184
|
+
creds[:file_contents] = config[:file_contents] if config[:file_contents]
|
|
185
|
+
creds
|
|
186
|
+
end
|
|
138
187
|
end
|
|
139
188
|
end
|
|
140
189
|
end
|
|
@@ -56,12 +56,23 @@ module LlmConductor
|
|
|
56
56
|
}
|
|
57
57
|
end
|
|
58
58
|
|
|
59
|
-
# Configure Google Gemini provider
|
|
60
|
-
|
|
59
|
+
# Configure Google Gemini provider (Generative Language API or Vertex AI)
|
|
60
|
+
#
|
|
61
|
+
# For the standard Generative Language API, provide api_key.
|
|
62
|
+
# For Vertex AI, provide project_id and optionally region (defaults to 'global').
|
|
63
|
+
# Authentication falls back to Application Default Credentials
|
|
64
|
+
# (ADC / GOOGLE_APPLICATION_CREDENTIALS) when neither file_path nor file_contents is supplied.
|
|
65
|
+
# Env vars (GEMINI_API_KEY, GOOGLE_VERTEX_PROJECT_ID, etc.) are only applied automatically
|
|
66
|
+
# on boot via setup_defaults_from_env — explicit calls use only what is passed.
|
|
67
|
+
def gemini(api_key: nil, project_id: nil, region: nil, file_path: nil, file_contents: nil, **options)
|
|
61
68
|
@providers[:gemini] = {
|
|
62
|
-
api_key
|
|
69
|
+
api_key:,
|
|
70
|
+
project_id:,
|
|
71
|
+
region: region || 'global',
|
|
72
|
+
file_path:,
|
|
73
|
+
file_contents:,
|
|
63
74
|
**options
|
|
64
|
-
}
|
|
75
|
+
}.compact
|
|
65
76
|
end
|
|
66
77
|
|
|
67
78
|
# Configure Groq provider
|
|
@@ -149,11 +160,22 @@ module LlmConductor
|
|
|
149
160
|
anthropic if ENV['ANTHROPIC_API_KEY']
|
|
150
161
|
openai if ENV['OPENAI_API_KEY']
|
|
151
162
|
openrouter if ENV['OPENROUTER_API_KEY']
|
|
152
|
-
|
|
163
|
+
setup_gemini_from_env
|
|
153
164
|
groq if ENV['GROQ_API_KEY']
|
|
154
165
|
zai if ENV['ZAI_API_KEY']
|
|
155
166
|
ollama # Always configure Ollama with default URL
|
|
156
167
|
end
|
|
168
|
+
|
|
169
|
+
def setup_gemini_from_env
|
|
170
|
+
return unless ENV.values_at('GEMINI_API_KEY', 'GOOGLE_VERTEX_PROJECT_ID').any?
|
|
171
|
+
|
|
172
|
+
gemini(
|
|
173
|
+
api_key: ENV['GEMINI_API_KEY'],
|
|
174
|
+
project_id: ENV['GOOGLE_VERTEX_PROJECT_ID'],
|
|
175
|
+
region: ENV['GOOGLE_VERTEX_REGION'],
|
|
176
|
+
file_contents: ENV['GOOGLE_CREDENTIALS_FILE_CONTENTS']
|
|
177
|
+
)
|
|
178
|
+
end
|
|
157
179
|
end
|
|
158
180
|
|
|
159
181
|
def self.configuration
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
# Patches the gemini-ai gem for two Vertex AI issues:
|
|
4
|
+
#
|
|
5
|
+
# 1. api_key + Vertex AI: the gem natively supports api_key only for
|
|
6
|
+
# generative-language-api. When both project_id and api_key are present,
|
|
7
|
+
# this patch rebuilds @base_address so the key is appended as ?key=... to
|
|
8
|
+
# the correct Vertex AI endpoint.
|
|
9
|
+
#
|
|
10
|
+
# 2. ADC (Application Default Credentials): the gem calls
|
|
11
|
+
# Google::Auth.get_application_default without a scope, which causes
|
|
12
|
+
# `invalid_scope` when exchanging service-account credentials for a token.
|
|
13
|
+
# This patch re-fetches the authorizer with the required cloud-platform scope.
|
|
14
|
+
module Gemini
|
|
15
|
+
module Controllers
|
|
16
|
+
class Client
|
|
17
|
+
module VertexAiPatch
|
|
18
|
+
CLOUD_PLATFORM_SCOPE = 'https://www.googleapis.com/auth/cloud-platform'
|
|
19
|
+
|
|
20
|
+
def initialize(config)
|
|
21
|
+
super
|
|
22
|
+
fix_vertex_api_key_base_address(config) if @authentication == :api_key && @service == 'vertex-ai-api'
|
|
23
|
+
fix_adc_scope if @authentication == :default_credentials
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
private
|
|
27
|
+
|
|
28
|
+
def fix_vertex_api_key_base_address(config)
|
|
29
|
+
project_id = config.dig(:credentials, :project_id)
|
|
30
|
+
|
|
31
|
+
if project_id.nil?
|
|
32
|
+
raise Errors::MissingProjectIdError,
|
|
33
|
+
'project_id is required for vertex-ai-api with api_key'
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
region = config.dig(:credentials, :region) || 'global'
|
|
37
|
+
@base_address = if region == 'global'
|
|
38
|
+
"https://aiplatform.googleapis.com/#{@service_version}/projects/#{project_id}/locations/#{region}"
|
|
39
|
+
else
|
|
40
|
+
"https://#{region}-aiplatform.googleapis.com/#{@service_version}/projects/#{project_id}/locations/#{region}"
|
|
41
|
+
end
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
def fix_adc_scope
|
|
45
|
+
@authorizer = ::Google::Auth.get_application_default(CLOUD_PLATFORM_SCOPE)
|
|
46
|
+
end
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
prepend VertexAiPatch
|
|
50
|
+
end
|
|
51
|
+
end
|
|
52
|
+
end
|
data/lib/llm_conductor.rb
CHANGED
|
@@ -29,7 +29,6 @@ module LlmConductor
|
|
|
29
29
|
end
|
|
30
30
|
|
|
31
31
|
# Unified generate method supporting both simple prompts and legacy template-based generation
|
|
32
|
-
# rubocop:disable Metrics/ParameterLists
|
|
33
32
|
def self.generate(model: nil, prompt: nil, type: nil, data: nil, vendor: nil, params: {})
|
|
34
33
|
if prompt && !type && !data
|
|
35
34
|
generate_simple_prompt(model:, prompt:, vendor:, params:)
|
|
@@ -40,7 +39,6 @@ module LlmConductor
|
|
|
40
39
|
"Invalid arguments. Use either: generate(prompt: 'text') or generate(type: :custom, data: {...})"
|
|
41
40
|
end
|
|
42
41
|
end
|
|
43
|
-
# rubocop:enable Metrics/ParameterLists
|
|
44
42
|
|
|
45
43
|
class << self
|
|
46
44
|
private
|
metadata
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: llm_conductor
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 1.
|
|
4
|
+
version: 1.7.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Ben Zheng
|
|
8
8
|
bindir: exe
|
|
9
9
|
cert_chain: []
|
|
10
|
-
date:
|
|
10
|
+
date: 2026-05-15 00:00:00.000000000 Z
|
|
11
11
|
dependencies:
|
|
12
12
|
- !ruby/object:Gem::Dependency
|
|
13
13
|
name: activesupport
|
|
@@ -181,6 +181,7 @@ files:
|
|
|
181
181
|
- lib/llm_conductor/clients/zai_client.rb
|
|
182
182
|
- lib/llm_conductor/configuration.rb
|
|
183
183
|
- lib/llm_conductor/data_builder.rb
|
|
184
|
+
- lib/llm_conductor/patches/gemini_vertex_api_key.rb
|
|
184
185
|
- lib/llm_conductor/prompt_manager.rb
|
|
185
186
|
- lib/llm_conductor/prompts.rb
|
|
186
187
|
- lib/llm_conductor/prompts/base_prompt.rb
|