Changeset 0.10.1 (#57)

This commit is contained in:
2026-02-24 16:51:08 +00:00
parent ea03f956ca
commit 13772ebd6c
11 changed files with 472 additions and 159 deletions

View File

@@ -1861,21 +1861,35 @@ func TestIntegration_Usage_PersonalIncludesBYOK(t *testing.T) {
_, adminToken := h.createAdminUser("admin", "admin@test.com")
database.TestDB.Exec("INSERT INTO platform_policies (key, value) VALUES ('allow_registration', 'true') ON CONFLICT (key) DO UPDATE SET value = 'true'")
database.TestDB.Exec("INSERT INTO platform_policies (key, value) VALUES ('default_user_active', 'true') ON CONFLICT (key) DO UPDATE SET value = 'true'")
database.TestDB.Exec("INSERT INTO platform_policies (key, value) VALUES ('allow_user_byok', 'true') ON CONFLICT (key) DO UPDATE SET value = 'true'")
userID, userToken := h.registerUser("carol", "carol@test.com", "password123")
// Create global provider
// Create global provider (admin-managed)
w := h.request("POST", "/api/v1/admin/configs", adminToken, map[string]interface{}{
"name": "Global2", "provider": "openai",
"endpoint": "https://api.openai.com/v1", "api_key": "sk-g2",
})
var cfg map[string]interface{}
decode(w, &cfg)
cfgID := cfg["id"].(string)
var globalCfg map[string]interface{}
decode(w, &globalCfg)
globalCfgID := globalCfg["id"].(string)
seedUsage(t, userID, cfgID, "gpt-4o", "global", 1000, 200, 0.01, 0.01)
seedUsage(t, userID, cfgID, "gpt-4o", "personal", 500, 100, 0.005, 0.005)
// Create personal BYOK provider (user-managed)
w = h.request("POST", "/api/v1/api-configs", userToken, map[string]interface{}{
"name": "MyKey", "provider": "openai",
"endpoint": "http://localhost:1/v1", "api_key": "sk-user-carol",
})
if w.Code != http.StatusCreated {
t.Fatalf("create personal config: want 201, got %d: %s", w.Code, w.Body.String())
}
var personalCfg map[string]interface{}
decode(w, &personalCfg)
personalCfgID := personalCfg["id"].(string)
// Personal view should include all scopes
// Seed usage against both providers
seedUsage(t, userID, globalCfgID, "gpt-4o", "global", 1000, 200, 0.01, 0.01)
seedUsage(t, userID, personalCfgID, "gpt-4o", "personal", 500, 100, 0.005, 0.005)
// Personal view should only show BYOK usage (not global)
w = h.request("GET", "/api/v1/usage", userToken, nil)
if w.Code != http.StatusOK {
t.Fatalf("personal usage: %d: %s", w.Code, w.Body.String())
@@ -1884,8 +1898,26 @@ func TestIntegration_Usage_PersonalIncludesBYOK(t *testing.T) {
decode(w, &resp)
totals := resp["totals"].(map[string]interface{})
if int(totals["requests"].(float64)) != 2 {
t.Errorf("personal should see 2 requests (includes BYOK), got %v", totals["requests"])
if int(totals["requests"].(float64)) != 1 {
t.Errorf("personal should see 1 request (BYOK only, not global), got %v", totals["requests"])
}
if int(totals["input_tokens"].(float64)) != 500 {
t.Errorf("personal should see 500 input tokens (BYOK row), got %v", totals["input_tokens"])
}
// Admin view should show global usage but exclude BYOK
w = h.request("GET", "/api/v1/admin/usage", adminToken, nil)
if w.Code != http.StatusOK {
t.Fatalf("admin usage: %d: %s", w.Code, w.Body.String())
}
decode(w, &resp)
totals = resp["totals"].(map[string]interface{})
if int(totals["requests"].(float64)) != 1 {
t.Errorf("admin should see 1 request (global only, not BYOK), got %v", totals["requests"])
}
if int(totals["input_tokens"].(float64)) != 1000 {
t.Errorf("admin should see 1000 input tokens (global row), got %v", totals["input_tokens"])
}
}