dsh-antigravity-auth 0.1.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.
- package/CHANGELOG.md +28 -0
- package/LICENSE +21 -0
- package/README.md +168 -0
- package/README.zh.md +159 -0
- package/cordis.patch.yml +12 -0
- package/lib/capability-lifecycle--tgGKajs.js +1896 -0
- package/lib/client.cjs +2123 -0
- package/lib/client.cjs.map +1 -0
- package/lib/image.js +564 -0
- package/lib/index.js +176 -0
- package/lib/invariant.js +2 -0
- package/lib/live-gate-runner.js +542 -0
- package/lib/live-gates.js +97 -0
- package/lib/llm-adapter.js +916 -0
- package/lib/media-admission.js +206 -0
- package/lib/private-failure-B9vzUkQ7.js +23 -0
- package/lib/private-transport-urF138qW.js +641 -0
- package/lib/private-transport.js +2 -0
- package/lib/project-context.js +133 -0
- package/lib/quota.js +283 -0
- package/lib/replay.js +156 -0
- package/lib/rpc-contract-BFWfdKKs.js +491 -0
- package/lib/rpc-contract.js +2 -0
- package/lib/safe-text-AlEyN8q_.js +12 -0
- package/lib/search.js +259 -0
- package/lib/status-D0-em3Ru.js +125 -0
- package/lib/types/auth-service.d.ts +64 -0
- package/lib/types/auth-service.d.ts.map +1 -0
- package/lib/types/auth-store.d.ts +45 -0
- package/lib/types/auth-store.d.ts.map +1 -0
- package/lib/types/bootstrap-service.d.ts +6 -0
- package/lib/types/bootstrap-service.d.ts.map +1 -0
- package/lib/types/capability-gates.d.ts +19 -0
- package/lib/types/capability-gates.d.ts.map +1 -0
- package/lib/types/capability-lifecycle.d.ts +26 -0
- package/lib/types/capability-lifecycle.d.ts.map +1 -0
- package/lib/types/client/AntigravityAuthSettings.d.ts +19 -0
- package/lib/types/client/AntigravityAuthSettings.d.ts.map +1 -0
- package/lib/types/client/index.d.ts +18 -0
- package/lib/types/client/index.d.ts.map +1 -0
- package/lib/types/client/locales.d.ts +121 -0
- package/lib/types/client/locales.d.ts.map +1 -0
- package/lib/types/client/styles.d.ts +4 -0
- package/lib/types/client/styles.d.ts.map +1 -0
- package/lib/types/credential-coordinator.d.ts +84 -0
- package/lib/types/credential-coordinator.d.ts.map +1 -0
- package/lib/types/image.d.ts +39 -0
- package/lib/types/image.d.ts.map +1 -0
- package/lib/types/index.d.ts +21 -0
- package/lib/types/index.d.ts.map +1 -0
- package/lib/types/invariant.d.ts +3 -0
- package/lib/types/invariant.d.ts.map +1 -0
- package/lib/types/live-gate-attachments.d.ts +6 -0
- package/lib/types/live-gate-attachments.d.ts.map +1 -0
- package/lib/types/live-gate-auth.d.ts +5 -0
- package/lib/types/live-gate-auth.d.ts.map +1 -0
- package/lib/types/live-gate-image.d.ts +5 -0
- package/lib/types/live-gate-image.d.ts.map +1 -0
- package/lib/types/live-gate-llm.d.ts +10 -0
- package/lib/types/live-gate-llm.d.ts.map +1 -0
- package/lib/types/live-gate-outcome.d.ts +8 -0
- package/lib/types/live-gate-outcome.d.ts.map +1 -0
- package/lib/types/live-gate-runner.d.ts +15 -0
- package/lib/types/live-gate-runner.d.ts.map +1 -0
- package/lib/types/live-gate-search.d.ts +5 -0
- package/lib/types/live-gate-search.d.ts.map +1 -0
- package/lib/types/live-gate-video.d.ts +8 -0
- package/lib/types/live-gate-video.d.ts.map +1 -0
- package/lib/types/live-gates.d.ts +25 -0
- package/lib/types/live-gates.d.ts.map +1 -0
- package/lib/types/llm-adapter.d.ts +65 -0
- package/lib/types/llm-adapter.d.ts.map +1 -0
- package/lib/types/login-types.d.ts +36 -0
- package/lib/types/login-types.d.ts.map +1 -0
- package/lib/types/media-admission.d.ts +54 -0
- package/lib/types/media-admission.d.ts.map +1 -0
- package/lib/types/model-catalog.d.ts +19 -0
- package/lib/types/model-catalog.d.ts.map +1 -0
- package/lib/types/oauth-flow.d.ts +87 -0
- package/lib/types/oauth-flow.d.ts.map +1 -0
- package/lib/types/private-failure.d.ts +6 -0
- package/lib/types/private-failure.d.ts.map +1 -0
- package/lib/types/private-transport-error.d.ts +13 -0
- package/lib/types/private-transport-error.d.ts.map +1 -0
- package/lib/types/private-transport.d.ts +48 -0
- package/lib/types/private-transport.d.ts.map +1 -0
- package/lib/types/project-context.d.ts +30 -0
- package/lib/types/project-context.d.ts.map +1 -0
- package/lib/types/quota.d.ts +43 -0
- package/lib/types/quota.d.ts.map +1 -0
- package/lib/types/raw-http.d.ts +11 -0
- package/lib/types/raw-http.d.ts.map +1 -0
- package/lib/types/replay.d.ts +30 -0
- package/lib/types/replay.d.ts.map +1 -0
- package/lib/types/rpc-contract.d.ts +33 -0
- package/lib/types/rpc-contract.d.ts.map +1 -0
- package/lib/types/rpc-vocabulary.d.ts +7 -0
- package/lib/types/rpc-vocabulary.d.ts.map +1 -0
- package/lib/types/rpc.d.ts +11 -0
- package/lib/types/rpc.d.ts.map +1 -0
- package/lib/types/safe-text.d.ts +3 -0
- package/lib/types/safe-text.d.ts.map +1 -0
- package/lib/types/search.d.ts +42 -0
- package/lib/types/search.d.ts.map +1 -0
- package/lib/types/status.d.ts +62 -0
- package/lib/types/status.d.ts.map +1 -0
- package/lib/types/video.d.ts +42 -0
- package/lib/types/video.d.ts.map +1 -0
- package/lib/types/wire-identity.d.ts +49 -0
- package/lib/types/wire-identity.d.ts.map +1 -0
- package/lib/video.js +320 -0
- package/lib/wire-identity.js +162 -0
- package/package.json +189 -0
- package/scripts/live-gates.mjs +4 -0
|
@@ -0,0 +1,206 @@
|
|
|
1
|
+
import { t as isBoundedSafeText } from "./safe-text-AlEyN8q_.js";
|
|
2
|
+
import { Buffer } from "node:buffer";
|
|
3
|
+
import { HarnessError } from "@deepseek-ai/dsh-llm";
|
|
4
|
+
//#region src/media-admission.ts
|
|
5
|
+
/** Shared Host-only media admission for image editing and the video POC. */
|
|
6
|
+
const DEFAULT_VIDEO_BYTES = 33554432;
|
|
7
|
+
const DEFAULT_INLINE_IMAGE_BYTES = 20971520;
|
|
8
|
+
const IMAGE_HANDLE_PATTERN = /^image:[^\s\p{C}]{1,256}$/u;
|
|
9
|
+
var MediaAdmissionError = class extends HarnessError {
|
|
10
|
+
constructor(message, code, options = {}) {
|
|
11
|
+
super(message, code, options);
|
|
12
|
+
}
|
|
13
|
+
};
|
|
14
|
+
function imageHandle(ref) {
|
|
15
|
+
return `image:${String(ref.attachmentId)}`;
|
|
16
|
+
}
|
|
17
|
+
/** Admit bounded, canonical image bytes and let AttachmentStore perform full decode validation. */
|
|
18
|
+
async function admitImageBytes(options, data, source, name = "antigravity-image", signal) {
|
|
19
|
+
throwIfAborted(signal);
|
|
20
|
+
const limits = options.attachments.imageLimits;
|
|
21
|
+
if (data.byteLength === 0 || data.byteLength > limits.maxImageBytes) throw new MediaAdmissionError("The image exceeds the deployment byte limit", "MEDIA_IMAGE_TOO_LARGE");
|
|
22
|
+
const mediaType = detectImageMediaType(data);
|
|
23
|
+
if (mediaType === void 0 || !limits.mediaTypes.includes(mediaType)) throw new MediaAdmissionError("The image media type or magic bytes are not supported", "MEDIA_IMAGE_INVALID");
|
|
24
|
+
const input = {
|
|
25
|
+
data,
|
|
26
|
+
mediaType,
|
|
27
|
+
name: safeName(name)
|
|
28
|
+
};
|
|
29
|
+
try {
|
|
30
|
+
await options.attachments.validateImage(input);
|
|
31
|
+
} catch {
|
|
32
|
+
throw new MediaAdmissionError("The image failed AttachmentStore admission", "MEDIA_IMAGE_INVALID");
|
|
33
|
+
}
|
|
34
|
+
return {
|
|
35
|
+
kind: "image",
|
|
36
|
+
input,
|
|
37
|
+
source
|
|
38
|
+
};
|
|
39
|
+
}
|
|
40
|
+
async function admitBase64Image(options, encoded, source = "inline", name, signal) {
|
|
41
|
+
const maxEncoded = Math.ceil(options.attachments.imageLimits.maxImageBytes / 3) * 4 + 4;
|
|
42
|
+
if (encoded.length === 0 || encoded.length > maxEncoded || !isCanonicalBase64(encoded)) throw new MediaAdmissionError("The encoded image is not bounded canonical base64", "MEDIA_IMAGE_INVALID");
|
|
43
|
+
let data;
|
|
44
|
+
try {
|
|
45
|
+
data = new Uint8Array(Buffer.from(encoded, "base64"));
|
|
46
|
+
} catch {
|
|
47
|
+
throw new MediaAdmissionError("The encoded image could not be decoded", "MEDIA_IMAGE_INVALID");
|
|
48
|
+
}
|
|
49
|
+
return admitImageBytes(options, data, source, name, signal);
|
|
50
|
+
}
|
|
51
|
+
/** Resolve one explicit session handle from durable session history; handles are not bearer capabilities. */
|
|
52
|
+
async function admitSessionImage(options, agent, handle, signal) {
|
|
53
|
+
throwIfAborted(signal);
|
|
54
|
+
if (!IMAGE_HANDLE_PATTERN.test(handle)) throw new MediaAdmissionError("The image handle is invalid", "MEDIA_HANDLE_INVALID");
|
|
55
|
+
const ref = authorizedSessionImages(agent).get(handle);
|
|
56
|
+
if (ref === void 0) throw new MediaAdmissionError("The image handle is not authorized by this session", "MEDIA_HANDLE_UNAUTHORIZED");
|
|
57
|
+
try {
|
|
58
|
+
const stored = await options.attachments.readImage(ref, signal);
|
|
59
|
+
return {
|
|
60
|
+
kind: "image",
|
|
61
|
+
input: {
|
|
62
|
+
data: stored.data,
|
|
63
|
+
mediaType: stored.ref.mediaType,
|
|
64
|
+
...stored.ref.name === void 0 ? {} : { name: stored.ref.name }
|
|
65
|
+
},
|
|
66
|
+
stored,
|
|
67
|
+
source: "session"
|
|
68
|
+
};
|
|
69
|
+
} catch {
|
|
70
|
+
throw new MediaAdmissionError("The authorized image could not be read", "MEDIA_IMAGE_READ_FAILED");
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
/** Resolve an image only after containment and regular-file checks, then admit its bytes. */
|
|
74
|
+
async function admitWorkspaceImage(options, workspace, path, signal) {
|
|
75
|
+
throwIfAborted(signal);
|
|
76
|
+
if (path.length === 0 || path.length > 4096 || /^https?:\/\//iu.test(path)) throw new MediaAdmissionError("The workspace image reference is invalid", "MEDIA_WORKSPACE_INVALID");
|
|
77
|
+
return admitImageBytes(options, await readStableWorkspaceBytes(options.fs, workspace, path, options.attachments.imageLimits.maxImageBytes, "image", signal), "workspace", basename(path), signal);
|
|
78
|
+
}
|
|
79
|
+
/** Admit an MP4 container without claiming native video attachment support. */
|
|
80
|
+
async function admitWorkspaceVideo(options, workspace, path, signal) {
|
|
81
|
+
throwIfAborted(signal);
|
|
82
|
+
if (path.length === 0 || path.length > 4096 || /^https?:\/\//iu.test(path)) throw new MediaAdmissionError("The workspace video reference is invalid", "MEDIA_VIDEO_INVALID");
|
|
83
|
+
const maxBytes = positive(options.maxVideoBytes, DEFAULT_VIDEO_BYTES);
|
|
84
|
+
const data = await readStableWorkspaceBytes(options.fs, workspace, path, maxBytes, "video", signal);
|
|
85
|
+
if (data.byteLength === 0 || data.byteLength > maxBytes || !isMp4(data)) throw new MediaAdmissionError("The workspace file is not a bounded MP4 video", "MEDIA_VIDEO_INVALID");
|
|
86
|
+
return {
|
|
87
|
+
kind: "video",
|
|
88
|
+
data,
|
|
89
|
+
mediaType: "video/mp4"
|
|
90
|
+
};
|
|
91
|
+
}
|
|
92
|
+
async function readStableWorkspaceBytes(fs, workspace, path, maxBytes, kind, signal) {
|
|
93
|
+
const symlinkCode = kind === "image" ? "MEDIA_WORKSPACE_SYMLINK" : "MEDIA_VIDEO_SYMLINK";
|
|
94
|
+
const regularCode = kind === "image" ? "MEDIA_WORKSPACE_NOT_REGULAR" : "MEDIA_VIDEO_NOT_REGULAR";
|
|
95
|
+
const containmentCode = kind === "image" ? "MEDIA_WORKSPACE_CONTAINMENT" : "MEDIA_VIDEO_CONTAINMENT";
|
|
96
|
+
const changedCode = kind === "image" ? "MEDIA_WORKSPACE_CHANGED" : "MEDIA_VIDEO_CHANGED";
|
|
97
|
+
const initialPath = await fs.lstat(path, { cwd: workspace }, signal);
|
|
98
|
+
if (initialPath?.type === "symlink") throw new MediaAdmissionError(`The workspace ${kind} is a symbolic link`, symlinkCode);
|
|
99
|
+
if (initialPath === void 0 || initialPath.type !== "file") throw new MediaAdmissionError(`The workspace ${kind} is not a regular file`, regularCode);
|
|
100
|
+
const root = await fs.resolve(workspace, fsResolveOptions(workspace, signal));
|
|
101
|
+
const target = await fs.resolve(path, fsResolveOptions(workspace, signal));
|
|
102
|
+
if (!fs.contains(root, target)) throw new MediaAdmissionError(`The workspace ${kind} is outside the active workspace`, containmentCode);
|
|
103
|
+
const before = await fs.stat(target, signal);
|
|
104
|
+
if (before === void 0 || before.type !== "file") throw new MediaAdmissionError(`The workspace ${kind} is not a regular file`, regularCode);
|
|
105
|
+
if (before.version !== initialPath.version) throw new MediaAdmissionError(`The workspace ${kind} changed before it could be read`, changedCode);
|
|
106
|
+
const data = await fs.readBytes(target, signal, maxBytes);
|
|
107
|
+
const finalPath = await fs.lstat(path, { cwd: workspace }, signal);
|
|
108
|
+
const finalTarget = await fs.resolve(path, fsResolveOptions(workspace, signal));
|
|
109
|
+
const after = await fs.stat(target, signal);
|
|
110
|
+
if (finalPath === void 0 || finalPath.type !== "file" || finalPath.version !== initialPath.version || finalTarget.targetKey !== target.targetKey || !fs.contains(root, finalTarget) || after === void 0 || after.type !== "file" || after.version !== before.version) throw new MediaAdmissionError(`The workspace ${kind} changed while it was being read`, changedCode);
|
|
111
|
+
return data;
|
|
112
|
+
}
|
|
113
|
+
function detectImageMediaType(data) {
|
|
114
|
+
if (data.length >= 8 && data[0] === 137 && data[1] === 80 && data[2] === 78 && data[3] === 71 && data[4] === 13 && data[5] === 10 && data[6] === 26 && data[7] === 10) return "image/png";
|
|
115
|
+
if (data.length >= 3 && data[0] === 255 && data[1] === 216 && data[2] === 255) return "image/jpeg";
|
|
116
|
+
if (data.length >= 12 && ascii(data, 0, 4) === "RIFF" && ascii(data, 8, 12) === "WEBP") return "image/webp";
|
|
117
|
+
if (data.length >= 6 && (ascii(data, 0, 6) === "GIF87a" || ascii(data, 0, 6) === "GIF89a")) return "image/gif";
|
|
118
|
+
}
|
|
119
|
+
function isMp4(data) {
|
|
120
|
+
return data.length >= 12 && ascii(data, 4, 8) === "ftyp";
|
|
121
|
+
}
|
|
122
|
+
/** Traverse durable session history once for both authorization and image listing. */
|
|
123
|
+
function sessionImageCatalog(agent) {
|
|
124
|
+
const result = /* @__PURE__ */ new Map();
|
|
125
|
+
const visited = /* @__PURE__ */ new WeakSet();
|
|
126
|
+
let sequence = 0;
|
|
127
|
+
let visitedNodes = 0;
|
|
128
|
+
const visit = (value, origin, depth = 0) => {
|
|
129
|
+
if (typeof value !== "object" || value === null || depth > 64 || visitedNodes >= 1e4 || visited.has(value)) return;
|
|
130
|
+
visited.add(value);
|
|
131
|
+
visitedNodes += 1;
|
|
132
|
+
if (Array.isArray(value)) {
|
|
133
|
+
for (const nested of value) visit(nested, origin, depth + 1);
|
|
134
|
+
return;
|
|
135
|
+
}
|
|
136
|
+
if (!isRecord(value)) return;
|
|
137
|
+
const attachment = value.type === "image" ? parseImageRef(value.attachment) : void 0;
|
|
138
|
+
if (attachment !== void 0) {
|
|
139
|
+
const handle = imageHandle(attachment);
|
|
140
|
+
if (!result.has(handle)) result.set(handle, {
|
|
141
|
+
handle,
|
|
142
|
+
attachment,
|
|
143
|
+
origin,
|
|
144
|
+
sequence: sequence++
|
|
145
|
+
});
|
|
146
|
+
}
|
|
147
|
+
if (value.type === "tool-result" && Array.isArray(value.content)) visit(value.content, origin, depth + 1);
|
|
148
|
+
};
|
|
149
|
+
for (const event of agent.session.events) {
|
|
150
|
+
const rawEvent = event;
|
|
151
|
+
if (!isRecord(rawEvent) || !isRecord(rawEvent.data)) continue;
|
|
152
|
+
if (rawEvent.type === "user/message") visit(rawEvent.data.content, "user");
|
|
153
|
+
else if (rawEvent.type === "assistant/message" && isRecord(rawEvent.data.message)) visit(rawEvent.data.message.content, "reference");
|
|
154
|
+
else if (rawEvent.type === "tool/result" && isRecord(rawEvent.data.message)) visit(rawEvent.data.message.content, "generated");
|
|
155
|
+
}
|
|
156
|
+
return [...result.values()];
|
|
157
|
+
}
|
|
158
|
+
function authorizedSessionImages(agent) {
|
|
159
|
+
return new Map(sessionImageCatalog(agent).map((entry) => [entry.handle, entry.attachment]));
|
|
160
|
+
}
|
|
161
|
+
function parseImageRef(value) {
|
|
162
|
+
if (!isRecord(value) || !isBoundedSafeText(value.attachmentId, 256) || value.mediaType !== "image/png" && value.mediaType !== "image/jpeg" && value.mediaType !== "image/webp" && value.mediaType !== "image/gif" || !isPositiveSafeInteger(value.bytes, 1073741824) || !isPositiveSafeInteger(value.width, 1e6) || !isPositiveSafeInteger(value.height, 1e6)) return void 0;
|
|
163
|
+
const name = typeof value.name === "string" && isBoundedSafeText(value.name, 256) ? safeName(value.name) : void 0;
|
|
164
|
+
return {
|
|
165
|
+
attachmentId: value.attachmentId,
|
|
166
|
+
mediaType: value.mediaType,
|
|
167
|
+
bytes: value.bytes,
|
|
168
|
+
width: value.width,
|
|
169
|
+
height: value.height,
|
|
170
|
+
...name === void 0 ? {} : { name }
|
|
171
|
+
};
|
|
172
|
+
}
|
|
173
|
+
function isPositiveSafeInteger(value, max) {
|
|
174
|
+
return Number.isSafeInteger(value) && value > 0 && value <= max;
|
|
175
|
+
}
|
|
176
|
+
function isCanonicalBase64(value) {
|
|
177
|
+
return /^(?:[A-Za-z0-9+/]{4})*(?:[A-Za-z0-9+/]{2}==|[A-Za-z0-9+/]{3}=)?$/u.test(value);
|
|
178
|
+
}
|
|
179
|
+
function safeName(value) {
|
|
180
|
+
const base = [...basename(value)].map((character) => character.charCodeAt(0) < 32 || character.charCodeAt(0) === 127 || character === "/" || character === "\\" ? "_" : character).join("").slice(0, 256);
|
|
181
|
+
return base.length > 0 ? base : "antigravity-image";
|
|
182
|
+
}
|
|
183
|
+
function basename(value) {
|
|
184
|
+
const normalized = value.replaceAll("\\", "/");
|
|
185
|
+
return normalized.slice(normalized.lastIndexOf("/") + 1);
|
|
186
|
+
}
|
|
187
|
+
function fsResolveOptions(cwd, signal) {
|
|
188
|
+
return signal === void 0 ? { cwd } : {
|
|
189
|
+
cwd,
|
|
190
|
+
signal
|
|
191
|
+
};
|
|
192
|
+
}
|
|
193
|
+
function ascii(data, start, end) {
|
|
194
|
+
return String.fromCharCode(...data.slice(start, end));
|
|
195
|
+
}
|
|
196
|
+
function positive(value, fallback) {
|
|
197
|
+
return value === void 0 || !Number.isFinite(value) || value <= 0 ? fallback : Math.min(Math.floor(value), 134217728);
|
|
198
|
+
}
|
|
199
|
+
function throwIfAborted(signal) {
|
|
200
|
+
if (signal !== void 0 && signal.aborted) throw new MediaAdmissionError("Media admission was cancelled", "MEDIA_CANCELLED");
|
|
201
|
+
}
|
|
202
|
+
function isRecord(value) {
|
|
203
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
204
|
+
}
|
|
205
|
+
//#endregion
|
|
206
|
+
export { DEFAULT_INLINE_IMAGE_BYTES, DEFAULT_VIDEO_BYTES, IMAGE_HANDLE_PATTERN, MediaAdmissionError, admitBase64Image, admitImageBytes, admitSessionImage, admitWorkspaceImage, admitWorkspaceVideo, detectImageMediaType, imageHandle, isMp4, sessionImageCatalog };
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import { m as PrivateTransportError } from "./private-transport-urF138qW.js";
|
|
2
|
+
//#region src/private-failure.ts
|
|
3
|
+
/** One closed classifier shared by every capability's public error vocabulary. */
|
|
4
|
+
function classifyPrivateFailure(error) {
|
|
5
|
+
if (!(error instanceof PrivateTransportError)) return "failed";
|
|
6
|
+
switch (error.code) {
|
|
7
|
+
case "authentication": return "authentication";
|
|
8
|
+
case "forbidden": return "forbidden";
|
|
9
|
+
case "rate-limited": return "rate-limited";
|
|
10
|
+
case "cancelled": return "cancelled";
|
|
11
|
+
case "timeout": return "timeout";
|
|
12
|
+
case "attribution-rejected": return "attribution-rejected";
|
|
13
|
+
case "protocol-drift":
|
|
14
|
+
case "invalid-response": return "protocol-drift";
|
|
15
|
+
case "response-too-large":
|
|
16
|
+
case "frame-too-large": return "response-limit";
|
|
17
|
+
case "request-too-large": return "request-limit";
|
|
18
|
+
case "upstream": return "upstream";
|
|
19
|
+
case "offline": return "network";
|
|
20
|
+
}
|
|
21
|
+
}
|
|
22
|
+
//#endregion
|
|
23
|
+
export { classifyPrivateFailure as t };
|