mirror of
https://github.com/diegosouzapw/OmniRoute.git
synced 2026-08-07 07:42:13 +03:00
[v3.8.50] fix(db/apiKeys): respect provider parameter in group model permission checks (fixes #8803) (#8817)
Validated in local merge-train T7 (ungrouped batch 2)
This commit is contained in:
@@ -1460,28 +1460,22 @@ export async function isModelAllowedForKey(
|
||||
}
|
||||
}
|
||||
|
||||
// Empty array means all models allowed
|
||||
if (!allowedModels || allowedModels.length === 0) {
|
||||
return true;
|
||||
}
|
||||
|
||||
let allowed = false;
|
||||
|
||||
// Check if model matches each allowed pattern
|
||||
// Support exact match and prefix match (e.g., "openai/*" allows all OpenAI models)
|
||||
for (const pattern of allowedModels) {
|
||||
if (modelPatternMatches(pattern, modelPermissionCandidates)) {
|
||||
allowed = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
let allowed =
|
||||
!allowedModels ||
|
||||
allowedModels.length === 0 ||
|
||||
allowedModels.some((pattern) => modelPatternMatches(pattern, modelPermissionCandidates));
|
||||
|
||||
// If key belongs to groups, also check group-level permissions
|
||||
// Extract model target and optional provider prefix if present (e.g. "openai/gpt-4" -> modelTarget: "gpt-4", provider: "openai")
|
||||
const hasProviderPrefix = modelId?.includes("/");
|
||||
const provider = hasProviderPrefix ? modelId.split("/")[0] : undefined;
|
||||
const modelTarget = hasProviderPrefix ? modelId.split("/").slice(1).join("/") : modelId || "";
|
||||
|
||||
// If key belongs to groups, check both modelTarget and full modelId against group rules
|
||||
if (metadata.id) {
|
||||
const groupAccess = checkKeyModelAccess(metadata.id, modelId || "");
|
||||
if (!groupAccess.allowed) {
|
||||
allowed = false;
|
||||
}
|
||||
const targetOk = checkKeyModelAccess(metadata.id, modelTarget, provider).allowed;
|
||||
const fullOk = checkKeyModelAccess(metadata.id, modelId || "", provider).allowed;
|
||||
if (!targetOk || !fullOk) allowed = false;
|
||||
}
|
||||
// Cache the result
|
||||
if (!usesSettingDependentClaudeRouting) {
|
||||
|
||||
44
tests/unit/group-provider-permission.test.ts
Normal file
44
tests/unit/group-provider-permission.test.ts
Normal file
@@ -0,0 +1,44 @@
|
||||
import test from "node:test";
|
||||
import assert from "node:assert/strict";
|
||||
|
||||
process.env.API_KEY_SECRET = "test-secret-key-for-unit-tests-123456789";
|
||||
|
||||
import * as apiKeys from "../../src/lib/db/apiKeys";
|
||||
import * as apiKeyGroups from "../../src/lib/db/apiKeyGroups";
|
||||
|
||||
test("isModelAllowedForKey respects provider parameter in checkKeyModelAccess", async () => {
|
||||
const createdKey = await apiKeys.createApiKey(
|
||||
"Group Provider Key",
|
||||
"test-machine-group-provider"
|
||||
);
|
||||
assert.ok(createdKey);
|
||||
|
||||
const group = apiKeyGroups.createKeyGroup("Provider Test Group", "Testing provider param");
|
||||
assert.ok(group);
|
||||
|
||||
apiKeyGroups.addKeyToGroup(createdKey.id, group.id);
|
||||
|
||||
apiKeyGroups.addGroupPermission(group.id, "gpt-4*", "deny", "openai");
|
||||
apiKeyGroups.addGroupPermission(group.id, "*", "allow");
|
||||
|
||||
const res1 = apiKeyGroups.checkKeyModelAccess(createdKey.id, "gpt-4", "openai");
|
||||
console.log("checkKeyModelAccess openai/gpt-4:", res1);
|
||||
|
||||
const res2 = apiKeyGroups.checkKeyModelAccess(createdKey.id, "gpt-4", "anthropic");
|
||||
console.log("checkKeyModelAccess anthropic/gpt-4:", res2);
|
||||
|
||||
// Model with provider "openai" matching pattern "gpt-4*" should be denied
|
||||
const allowedOpenAIDenied = await apiKeys.isModelAllowedForKey(createdKey.key, "openai/gpt-4");
|
||||
assert.equal(
|
||||
allowedOpenAIDenied,
|
||||
false,
|
||||
"openai/gpt-4 should be denied by provider-specific rule"
|
||||
);
|
||||
|
||||
// Model with provider "anthropic" matching pattern "gpt-4*" should NOT trigger the openai-specific deny rule
|
||||
const allowedAnthropicAllowed = await apiKeys.isModelAllowedForKey(
|
||||
createdKey.key,
|
||||
"anthropic/gpt-4"
|
||||
);
|
||||
assert.equal(allowedAnthropicAllowed, true, "anthropic/gpt-4 should be allowed");
|
||||
});
|
||||
Reference in New Issue
Block a user