@automagik/omni 2.260717.2 → 2.260717.4
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.
- package/dist/index.js +1 -1
- package/dist/server/index.js +58 -17
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -125164,7 +125164,7 @@ import { fileURLToPath } from "url";
|
|
|
125164
125164
|
// package.json
|
|
125165
125165
|
var package_default = {
|
|
125166
125166
|
name: "@automagik/omni",
|
|
125167
|
-
version: "2.260717.
|
|
125167
|
+
version: "2.260717.4",
|
|
125168
125168
|
description: "LLM-optimized CLI for Omni",
|
|
125169
125169
|
type: "module",
|
|
125170
125170
|
bin: {
|
package/dist/server/index.js
CHANGED
|
@@ -225883,7 +225883,7 @@ var init_sentry_scrub = __esm(() => {
|
|
|
225883
225883
|
var require_package7 = __commonJS((exports, module) => {
|
|
225884
225884
|
module.exports = {
|
|
225885
225885
|
name: "@omni/api",
|
|
225886
|
-
version: "2.260717.
|
|
225886
|
+
version: "2.260717.4",
|
|
225887
225887
|
type: "module",
|
|
225888
225888
|
exports: {
|
|
225889
225889
|
".": {
|
|
@@ -285026,11 +285026,9 @@ var init_genie_signature = __esm(() => {
|
|
|
285026
285026
|
}
|
|
285027
285027
|
}, 401);
|
|
285028
285028
|
}
|
|
285029
|
-
if (outcome.status === "verified"
|
|
285029
|
+
if (outcome.status === "verified") {
|
|
285030
285030
|
c.set("signedBy", outcome.hostId);
|
|
285031
|
-
|
|
285032
|
-
c.set("signedByScopes", outcome.hostScopes);
|
|
285033
|
-
}
|
|
285031
|
+
c.set("signedByScopes", outcome.hostScopes);
|
|
285034
285032
|
services.genieHosts.touchLastSeen(outcome.hostId).catch((err) => {
|
|
285035
285033
|
log59.warn("touchLastSeen failed (non-fatal)", { hostId: outcome.hostId, err: String(err) });
|
|
285036
285034
|
});
|
|
@@ -285685,6 +285683,18 @@ var init_scopes = __esm(() => {
|
|
|
285685
285683
|
};
|
|
285686
285684
|
});
|
|
285687
285685
|
|
|
285686
|
+
// ../api/src/lib/signed-host-scope-context.ts
|
|
285687
|
+
function readSignedHostScopeContext(c) {
|
|
285688
|
+
const hostId = c.get("signedBy");
|
|
285689
|
+
if (!hostId)
|
|
285690
|
+
return { kind: "unsigned" };
|
|
285691
|
+
const scopes = c.get("signedByScopes");
|
|
285692
|
+
if (!Array.isArray(scopes) || !scopes.every((scope) => typeof scope === "string")) {
|
|
285693
|
+
return { kind: "invalid", hostId };
|
|
285694
|
+
}
|
|
285695
|
+
return { kind: "valid", hostId, scopes };
|
|
285696
|
+
}
|
|
285697
|
+
|
|
285688
285698
|
// ../api/src/middleware/scope-enforcer.ts
|
|
285689
285699
|
function buildSegmentRegex(patternPath) {
|
|
285690
285700
|
const escaped = patternPath.split("/").map((seg) => seg.startsWith(":") ? "[^/]+" : seg.replace(/[.*+?^${}()|[\]\\]/g, "\\$&")).join("/");
|
|
@@ -285852,6 +285862,16 @@ function lockDenyResponse(c, lock, result) {
|
|
|
285852
285862
|
}
|
|
285853
285863
|
}, 403);
|
|
285854
285864
|
}
|
|
285865
|
+
function invalidSignedHostScopeContextResponse(c, hostId) {
|
|
285866
|
+
log61.warn(`DENIED: signedBy=${hostId} route=${c.req.method.toUpperCase()} ${c.req.path} host-scopes=INVALID`);
|
|
285867
|
+
return c.json({
|
|
285868
|
+
error: {
|
|
285869
|
+
code: "FORBIDDEN",
|
|
285870
|
+
message: "Signing host scope context is missing.",
|
|
285871
|
+
host: hostId
|
|
285872
|
+
}
|
|
285873
|
+
}, 403);
|
|
285874
|
+
}
|
|
285855
285875
|
var log61, OUTBOUND_SEND_PREFIXES, PATH_INSTANCE_PREFIXES, PATH_CHAT_PREFIXES, PATH_MEDIA_INSTANCE_PREFIX = "/media/", scopeEnforcerMiddleware;
|
|
285856
285876
|
var init_scope_enforcer = __esm(() => {
|
|
285857
285877
|
init_src();
|
|
@@ -285875,8 +285895,9 @@ var init_scope_enforcer = __esm(() => {
|
|
|
285875
285895
|
}
|
|
285876
285896
|
const method = c.req.method.toUpperCase();
|
|
285877
285897
|
const path2 = c.req.path;
|
|
285878
|
-
const
|
|
285879
|
-
|
|
285898
|
+
const signedHost = readSignedHostScopeContext(c);
|
|
285899
|
+
if (signedHost.kind === "invalid")
|
|
285900
|
+
return invalidSignedHostScopeContextResponse(c, signedHost.hostId);
|
|
285880
285901
|
const wildcard = ApiKeyService.scopeAllows(apiKey.scopes, "*");
|
|
285881
285902
|
let requiredScope;
|
|
285882
285903
|
if (!wildcard) {
|
|
@@ -285900,8 +285921,9 @@ var init_scope_enforcer = __esm(() => {
|
|
|
285900
285921
|
}, 403);
|
|
285901
285922
|
}
|
|
285902
285923
|
}
|
|
285903
|
-
if (
|
|
285904
|
-
const
|
|
285924
|
+
if (signedHost.kind === "valid") {
|
|
285925
|
+
const { hostId: signedBy, scopes: hostScopes } = signedHost;
|
|
285926
|
+
const hostWildcard = ApiKeyService.scopeAllows(hostScopes, "*");
|
|
285905
285927
|
if (!hostWildcard) {
|
|
285906
285928
|
const needed = requiredScope ?? findRequiredScope(method, path2);
|
|
285907
285929
|
if (!needed) {
|
|
@@ -285913,8 +285935,8 @@ var init_scope_enforcer = __esm(() => {
|
|
|
285913
285935
|
}
|
|
285914
285936
|
}, 403);
|
|
285915
285937
|
}
|
|
285916
|
-
if (!ApiKeyService.scopeAllows(
|
|
285917
|
-
log61.warn(`DENIED: signedBy=${signedBy} route=${method} ${path2} required=${needed} host-scopes=${
|
|
285938
|
+
if (!ApiKeyService.scopeAllows(hostScopes, needed)) {
|
|
285939
|
+
log61.warn(`DENIED: signedBy=${signedBy} route=${method} ${path2} required=${needed} host-scopes=${hostScopes.join(",")}`);
|
|
285918
285940
|
return c.json({
|
|
285919
285941
|
error: {
|
|
285920
285942
|
code: "FORBIDDEN",
|
|
@@ -356775,15 +356797,29 @@ function normalizeOverrides(overrides) {
|
|
|
356775
356797
|
denylistPresetKey: overrides.denylistPresetKey === null ? undefined : overrides.denylistPresetKey
|
|
356776
356798
|
};
|
|
356777
356799
|
}
|
|
356778
|
-
function
|
|
356779
|
-
|
|
356780
|
-
|
|
356800
|
+
function invalidSignedHostScopeContextResponse2(c, hostId) {
|
|
356801
|
+
return c.json({
|
|
356802
|
+
error: {
|
|
356803
|
+
code: "FORBIDDEN",
|
|
356804
|
+
message: "Signing host scope context is missing.",
|
|
356805
|
+
host: hostId
|
|
356806
|
+
}
|
|
356807
|
+
}, 403);
|
|
356808
|
+
}
|
|
356809
|
+
function enforceScopeCeiling(c, requestedScopes) {
|
|
356810
|
+
const authorizerScopeSets = [c.get("apiKey")?.scopes ?? []];
|
|
356811
|
+
const signedHost = readSignedHostScopeContext(c);
|
|
356812
|
+
if (signedHost.kind === "invalid")
|
|
356813
|
+
return invalidSignedHostScopeContextResponse2(c, signedHost.hostId);
|
|
356814
|
+
if (signedHost.kind === "valid")
|
|
356815
|
+
authorizerScopeSets.push(signedHost.scopes);
|
|
356816
|
+
const exceeding = requestedScopes.filter((scope) => authorizerScopeSets.some((authorizerScopes) => !ApiKeyService.scopeAllows(authorizerScopes, scope)));
|
|
356781
356817
|
if (exceeding.length === 0)
|
|
356782
356818
|
return null;
|
|
356783
356819
|
return c.json({
|
|
356784
356820
|
error: {
|
|
356785
356821
|
code: "FORBIDDEN",
|
|
356786
|
-
message: `Cannot
|
|
356822
|
+
message: `Cannot grant scopes that exceed the caller's own. Disallowed: ${exceeding.join(", ")}`
|
|
356787
356823
|
}
|
|
356788
356824
|
}, 403);
|
|
356789
356825
|
}
|
|
@@ -356798,7 +356834,7 @@ async function handleProfileCreate(c, data, services) {
|
|
|
356798
356834
|
overrides: normalizeOverrides(data.overrides),
|
|
356799
356835
|
denylistPresetKey: data.denylistPresetKey
|
|
356800
356836
|
});
|
|
356801
|
-
const ceilingDenied =
|
|
356837
|
+
const ceilingDenied = enforceScopeCeiling(c, resolved.scopes);
|
|
356802
356838
|
if (ceilingDenied)
|
|
356803
356839
|
return ceilingDenied;
|
|
356804
356840
|
const result = await services.apiKeys.create({
|
|
@@ -356833,7 +356869,7 @@ async function handleLegacyCreate(c, data, services) {
|
|
|
356833
356869
|
if (!data.scopes || data.scopes.length === 0) {
|
|
356834
356870
|
return c.json({ error: { code: "VALIDATION_ERROR", message: "scopes is required when no profile is supplied" } }, 400);
|
|
356835
356871
|
}
|
|
356836
|
-
const ceilingDenied =
|
|
356872
|
+
const ceilingDenied = enforceScopeCeiling(c, data.scopes);
|
|
356837
356873
|
if (ceilingDenied)
|
|
356838
356874
|
return ceilingDenied;
|
|
356839
356875
|
const result = await services.apiKeys.create({
|
|
@@ -356957,6 +356993,11 @@ var init_keys = __esm(() => {
|
|
|
356957
356993
|
const id = c.req.param("id");
|
|
356958
356994
|
const data = c.req.valid("json");
|
|
356959
356995
|
const services = c.get("services");
|
|
356996
|
+
if (data.scopes) {
|
|
356997
|
+
const ceilingDenied = enforceScopeCeiling(c, data.scopes);
|
|
356998
|
+
if (ceilingDenied)
|
|
356999
|
+
return ceilingDenied;
|
|
357000
|
+
}
|
|
356960
357001
|
try {
|
|
356961
357002
|
const updated = await services.apiKeys.update(id, {
|
|
356962
357003
|
...data,
|