Skip to content

Commit 62b0889

Browse files
Merge pull request #1175 from blublinsky/additional-providers
add additional vllm based providers
2 parents f7bbfeb + 8caa886 commit 62b0889

File tree

2 files changed

+114
-16
lines changed

2 files changed

+114
-16
lines changed

internal/controller/lcore/assets_test.go

Lines changed: 91 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -65,8 +65,9 @@ func TestBuildLlamaStackYAML_SupportedProvider(t *testing.T) {
6565
}
6666

6767
func TestBuildLlamaStackYAML_UnsupportedProvider(t *testing.T) {
68-
// Test unsupported providers
69-
unsupportedProviders := []string{"watsonx", "bam", "rhoai_vllm", "rhelai_vllm"}
68+
// Test unsupported providers (watsonx, bam are not supported)
69+
// Note: rhoai_vllm and rhelai_vllm are now supported via OpenAI compatibility
70+
unsupportedProviders := []string{"watsonx", "bam"}
7071

7172
for _, providerType := range unsupportedProviders {
7273
t.Run(providerType, func(t *testing.T) {
@@ -116,6 +117,94 @@ func TestBuildLlamaStackYAML_UnsupportedProvider(t *testing.T) {
116117
}
117118
}
118119

120+
func TestBuildLlamaStackYAML_OpenAICompatibleProviders(t *testing.T) {
121+
// Test that vLLM providers (rhoai_vllm, rhelai_vllm) use remote::vllm provider type
122+
vllmProviders := []string{"rhoai_vllm", "rhelai_vllm"}
123+
124+
for _, providerType := range vllmProviders {
125+
t.Run(providerType, func(t *testing.T) {
126+
// Create a test CR with vLLM provider
127+
cr := &olsv1alpha1.OLSConfig{
128+
Spec: olsv1alpha1.OLSConfigSpec{
129+
LLMConfig: olsv1alpha1.LLMSpec{
130+
Providers: []olsv1alpha1.ProviderSpec{
131+
{
132+
Name: "test-provider",
133+
Type: providerType,
134+
URL: "https://test-vllm-endpoint.com/v1",
135+
Models: []olsv1alpha1.ModelSpec{
136+
{Name: "test-model"},
137+
},
138+
},
139+
},
140+
},
141+
},
142+
}
143+
144+
// Build the YAML - should succeed
145+
ctx := context.Background()
146+
yamlOutput, err := buildLlamaStackYAML(nil, ctx, cr)
147+
148+
// Verify no error is returned
149+
if err != nil {
150+
t.Fatalf("Unexpected error for supported provider '%s': %v", providerType, err)
151+
}
152+
153+
// Verify it's valid YAML
154+
var result map[string]interface{}
155+
err = yaml.Unmarshal([]byte(yamlOutput), &result)
156+
if err != nil {
157+
t.Fatalf("buildLlamaStackYAML produced invalid YAML for '%s': %v", providerType, err)
158+
}
159+
160+
// Verify provider is configured as remote::vllm
161+
providers, ok := result["providers"].(map[string]interface{})
162+
if !ok {
163+
t.Fatalf("providers section not found or invalid type")
164+
}
165+
166+
inference, ok := providers["inference"].([]interface{})
167+
if !ok || len(inference) == 0 {
168+
t.Fatalf("inference providers not found or empty")
169+
}
170+
171+
// Find the test provider (not the sentence-transformers one)
172+
var testProvider map[string]interface{}
173+
for _, provider := range inference {
174+
p, ok := provider.(map[string]interface{})
175+
if !ok {
176+
continue
177+
}
178+
if p["provider_id"] == "test-provider" {
179+
testProvider = p
180+
break
181+
}
182+
}
183+
184+
if testProvider == nil {
185+
t.Fatalf("Test provider not found in inference providers")
186+
}
187+
188+
// Verify it's configured as vLLM (not OpenAI)
189+
if testProvider["provider_type"] != "remote::vllm" {
190+
t.Errorf("Expected provider_type 'remote::vllm' for %s, got '%v'", providerType, testProvider["provider_type"])
191+
}
192+
193+
// Verify URL is present in config
194+
config, ok := testProvider["config"].(map[string]interface{})
195+
if !ok {
196+
t.Fatalf("provider config not found or invalid type")
197+
}
198+
199+
if url, ok := config["url"].(string); !ok || url == "" {
200+
t.Errorf("Expected URL to be configured for %s provider", providerType)
201+
}
202+
203+
t.Logf("Successfully validated '%s' provider uses remote::vllm", providerType)
204+
})
205+
}
206+
}
207+
119208
func TestBuildLlamaStackYAML_AzureProvider(t *testing.T) {
120209
// Create a fake secret with API token for Azure provider
121210
secret := &corev1.Secret{

internal/controller/lcore/config.go

Lines changed: 23 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -74,15 +74,16 @@ func buildLlamaStackCoreConfig(_ reconciler.Reconciler, _ *olsv1alpha1.OLSConfig
7474
return map[string]interface{}{
7575
"version": "2",
7676
"image_name": "minimal-viable-llama-stack-configuration",
77-
// Minimal APIs for RAG + MCP: agents (for MCP), files, inference, safety (required by agents), tool_runtime, vector_io
78-
// Commented out: datasetio, eval, post_training, scoring, telemetry (not available in this Llama Stack version)
79-
"apis": []string{"agents" /* "datasetio", "eval", */, "files", "inference" /* , "post_training", */, "safety" /* , "scoring", "telemetry" */, "tool_runtime", "vector_io"},
77+
// Minimal APIs for RAG + MCP: agents (for MCP), files, inference, safety (required by agents), telemetry, tool_runtime, vector_io
78+
// Commented out: datasetio, eval, post_training, scoring (not needed for basic RAG + MCP)
79+
// Commented out: datasetio, eval, post_training, prompts, scoring, telemetry
80+
"apis": []string{"agents" /* "datasetio", "eval", */, "files", "inference" /* , "post_training", */, "safety" /* , "scoring", "telemetry"*/, "tool_runtime", "vector_io"},
8081
"benchmarks": []interface{}{},
8182
"container_image": nil,
8283
"datasets": []interface{}{},
8384
"external_providers_dir": nil,
8485
"inference_store": map[string]interface{}{
85-
"db_path": "/tmp/llama-stack/inference_store.db",
86+
"db_path": ".llama/distributions/ollama/inference_store.db",
8687
"type": "sqlite",
8788
},
8889
"logging": nil,
@@ -205,15 +206,23 @@ func buildLlamaStackInferenceProviders(_ reconciler.Reconciler, _ context.Contex
205206
envVarName := utils.ProviderNameToEnvVarName(provider.Name)
206207

207208
// Map OLSConfig provider types to Llama Stack provider types
208-
// Note: Only providers supported by Llama Stack are included
209209
switch provider.Type {
210-
case "openai":
211-
providerConfig["provider_type"] = "remote::openai"
210+
case "openai", "rhoai_vllm", "rhelai_vllm":
212211
config := map[string]interface{}{}
213-
214-
// Set environment variable name for API key
215-
// Llama Stack will substitute ${env.VAR_NAME} with the actual env var value
216-
config["api_key"] = fmt.Sprintf("${env.%s_API_KEY}", envVarName)
212+
// Determine the appropriate Llama Stack provider type
213+
// - OpenAI uses remote::openai (validates against OpenAI model whitelist)
214+
// - vLLM uses remote::vllm (accepts any custom model names)
215+
if provider.Type == "openai" {
216+
providerConfig["provider_type"] = "remote::openai"
217+
// Set API key from environment variable
218+
// Llama Stack will substitute ${env.VAR_NAME} with the actual env var value
219+
config["api_key"] = fmt.Sprintf("${env.%s_API_KEY}", envVarName)
220+
} else {
221+
providerConfig["provider_type"] = "remote::vllm"
222+
// Set API key from environment variable
223+
// Llama Stack will substitute ${env.VAR_NAME} with the actual env var value
224+
config["api_token"] = fmt.Sprintf("${env.%s_API_KEY}", envVarName)
225+
}
217226

218227
// Add custom URL if specified
219228
if provider.URL != "" {
@@ -246,14 +255,14 @@ func buildLlamaStackInferenceProviders(_ reconciler.Reconciler, _ context.Contex
246255
}
247256
providerConfig["config"] = config
248257

249-
case "watsonx", "rhoai_vllm", "rhelai_vllm", "bam":
258+
case "watsonx", "bam":
250259
// These providers are not supported by Llama Stack
251260
// They are handled directly by lightspeed-stack (LCS), not Llama Stack
252-
return nil, fmt.Errorf("provider type '%s' (provider '%s') is not currently supported by Llama Stack. Supported types: openai, azure_openai", provider.Type, provider.Name)
261+
return nil, fmt.Errorf("provider type '%s' (provider '%s') is not currently supported by Llama Stack. Supported types: openai, azure_openai, rhoai_vllm, rhelai_vllm", provider.Type, provider.Name)
253262

254263
default:
255264
// Unknown provider type
256-
return nil, fmt.Errorf("unknown provider type '%s' (provider '%s'). Supported types: openai, azure_openai", provider.Type, provider.Name)
265+
return nil, fmt.Errorf("unknown provider type '%s' (provider '%s'). Supported types: openai, azure_openai, rhoai_vllm, rhelai_vllm", provider.Type, provider.Name)
257266
}
258267

259268
providers = append(providers, providerConfig)

0 commit comments

Comments
 (0)