@playdrop/playdrop-cli 0.11.0 → 0.11.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.
@@ -1,5 +1,5 @@
1
1
  {
2
- "version": "0.11.0",
2
+ "version": "0.11.4",
3
3
  "build": 1,
4
4
  "runtimeSdkVersion": "0.10.0",
5
5
  "clients": {
@@ -48,7 +48,6 @@ const SDK_REFERENCE_PATTERNS = [
48
48
  const SDK_INIT_PATTERNS = [
49
49
  /\bwindow\s*\.\s*playdrop\s*\.\s*init\s*\(/g,
50
50
  /\bplaydrop\s*\.\s*init\s*\(/g,
51
- /\bsdk\s*\.\s*initialize\s*\(/g,
52
51
  ];
53
52
  const SDK_READY_PATTERNS = [
54
53
  /\bsdk\s*\??\.\s*host\s*\??\.\s*ready\s*\(/g,
@@ -16,6 +16,7 @@ const FRAME_SELECTOR = 'iframe[title="Game"]';
16
16
  exports.CAPTURE_LOG_LEVEL_VALUES = ['debug', 'info', 'warn', 'error'];
17
17
  exports.MAX_CAPTURE_TIMEOUT_SECONDS = 600;
18
18
  const GOOGLE_TELEMETRY_HOSTS = [
19
+ 'analytics.google.com',
19
20
  'googletagmanager.com',
20
21
  'google-analytics.com',
21
22
  'googleadservices.com',
@@ -97,7 +98,13 @@ function extractRefusedResourceUrls(text) {
97
98
  }
98
99
  function isKnownGoogleTelemetryConsoleIssue(text, locationUrl) {
99
100
  if (/Content Security Policy/i.test(text)) {
100
- return extractRefusedResourceUrls(text).some(isKnownGoogleTelemetryUrl);
101
+ const refusedUrls = extractRefusedResourceUrls(text);
102
+ if (refusedUrls.some(isKnownGoogleTelemetryUrl)) {
103
+ return true;
104
+ }
105
+ const messageUrls = extractHttpUrls(text);
106
+ return messageUrls.some(isKnownGoogleTelemetryUrl)
107
+ && !messageUrls.some(isLoopbackOrLocalUrl);
101
108
  }
102
109
  if (!/ERR_BLOCKED_BY_CLIENT/i.test(text)) {
103
110
  return false;
@@ -9,6 +9,7 @@ type CaptureRemoteOptions = {
9
9
  loginUrl?: string;
10
10
  actions?: string;
11
11
  viewport?: string;
12
+ surface?: string;
12
13
  fpsSampleMs?: string | number;
13
14
  };
14
15
  export declare function buildCaptureRemoteCommandArgs(url: string | undefined, options?: CaptureRemoteOptions): string[] | null;
@@ -10,6 +10,29 @@ const http_1 = require("../http");
10
10
  const messages_1 = require("../messages");
11
11
  const devShared_1 = require("./devShared");
12
12
  const captureRuntime_1 = require("../captureRuntime");
13
+ const MOBILE_USER_AGENT = 'Mozilla/5.0 (iPhone; CPU iPhone OS 16_0 like Mac OS X) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/16.0 Mobile/15E148 Safari/604.1';
14
+ const SURFACE_CONTEXT_OPTIONS = {
15
+ desktop: {
16
+ viewport: { width: 1280, height: 720 },
17
+ deviceScaleFactor: 1,
18
+ isMobile: false,
19
+ hasTouch: false,
20
+ },
21
+ 'mobile-landscape': {
22
+ viewport: { width: 896, height: 414 },
23
+ deviceScaleFactor: 2,
24
+ isMobile: true,
25
+ hasTouch: true,
26
+ userAgent: MOBILE_USER_AGENT,
27
+ },
28
+ 'mobile-portrait': {
29
+ viewport: { width: 414, height: 896 },
30
+ deviceScaleFactor: 2,
31
+ isMobile: true,
32
+ hasTouch: true,
33
+ userAgent: MOBILE_USER_AGENT,
34
+ },
35
+ };
13
36
  function readUnsupportedPlaydropCaptureMessage(targetUrl) {
14
37
  let parsed;
15
38
  try {
@@ -69,6 +92,16 @@ function parseViewport(raw) {
69
92
  }
70
93
  return { width, height };
71
94
  }
95
+ function parseSurface(raw) {
96
+ const normalized = raw?.trim().toLowerCase();
97
+ if (!normalized) {
98
+ return null;
99
+ }
100
+ if (normalized === 'desktop' || normalized === 'mobile-landscape' || normalized === 'mobile-portrait') {
101
+ return normalized;
102
+ }
103
+ throw new Error('invalid_surface');
104
+ }
72
105
  function parseFpsSampleMs(raw) {
73
106
  if (raw === undefined) {
74
107
  return null;
@@ -172,6 +205,7 @@ function buildCaptureRemoteCommandArgs(url, options = {}) {
172
205
  pushOptionalArg(args, '--expected-url', options.expectedUrl);
173
206
  pushOptionalArg(args, '--actions', options.actions);
174
207
  pushOptionalArg(args, '--viewport', options.viewport);
208
+ pushOptionalArg(args, '--surface', options.surface);
175
209
  if (options.fpsSampleMs !== undefined) {
176
210
  args.push('--fps-sample-ms', String(parseFpsSampleMs(options.fpsSampleMs)));
177
211
  }
@@ -205,6 +239,7 @@ function parseOptions(url, options = {}) {
205
239
  logPath: options.log?.trim() ? (0, node_path_1.resolve)(process.cwd(), options.log.trim()) : null,
206
240
  actionsPath: options.actions?.trim() ? (0, node_path_1.resolve)(process.cwd(), options.actions.trim()) : null,
207
241
  viewport: parseViewport(options.viewport),
242
+ surface: parseSurface(options.surface),
208
243
  fpsSampleMs: parseFpsSampleMs(options.fpsSampleMs),
209
244
  login: username
210
245
  ? {
@@ -247,6 +282,11 @@ async function captureRemote(url, options = {}) {
247
282
  process.exitCode = 1;
248
283
  return;
249
284
  }
285
+ if (error instanceof Error && error.message === 'invalid_surface') {
286
+ (0, messages_1.printErrorWithHelp)('The --surface value must be desktop, mobile-landscape, or mobile-portrait.', [], { command: 'project capture remote' });
287
+ process.exitCode = 1;
288
+ return;
289
+ }
250
290
  if (error instanceof Error && error.message === 'invalid_fps_sample_ms') {
251
291
  (0, messages_1.printErrorWithHelp)('The --fps-sample-ms value must be an integer between 100 and 60000 milliseconds.', [], { command: 'project capture remote' });
252
292
  process.exitCode = 1;
@@ -318,7 +358,11 @@ async function captureRemote(url, options = {}) {
318
358
  user: parsed.login ? undefined : currentUser,
319
359
  login: parsed.login,
320
360
  actions: actions ?? undefined,
321
- contextOptions: parsed.viewport ? { viewport: parsed.viewport } : undefined,
361
+ contextOptions: parsed.surface
362
+ ? { ...SURFACE_CONTEXT_OPTIONS[parsed.surface], ...(parsed.viewport ? { viewport: parsed.viewport } : {}) }
363
+ : parsed.viewport
364
+ ? { viewport: parsed.viewport }
365
+ : undefined,
322
366
  frameRateSampleMs: parsed.fpsSampleMs ?? undefined,
323
367
  });
324
368
  if (result.errorCount > 0) {
@@ -77,6 +77,7 @@ type TaskCatalogueReportOptions = {
77
77
  type TaskCompleteOptions = {
78
78
  env?: string;
79
79
  nextSteps?: string;
80
+ summary?: string;
80
81
  };
81
82
  type TaskClaimSlugOptions = {
82
83
  appName?: string;
@@ -98,6 +99,10 @@ type TaskSubmitReviewOptions = {
98
99
  evidenceDir?: string;
99
100
  nextSteps?: string;
100
101
  };
102
+ type TaskSubmitEvalOptions = {
103
+ env?: string;
104
+ resultFile?: string;
105
+ };
101
106
  export type WorkerHealthAlertInput = {
102
107
  state: 'started' | 'stopped' | 'crashed';
103
108
  env: string;
@@ -157,6 +162,10 @@ export declare function stagePlaydropPluginReferences(input: {
157
162
  pluginRoot: string;
158
163
  kind: AgentTaskKind;
159
164
  }): Promise<string[]>;
165
+ export declare function stageAssignmentPluginBundle(input: {
166
+ workspaceDir: string;
167
+ pluginBundle: NonNullable<WorkerAgentTaskAssignmentResponse['pluginBundle']>;
168
+ }): Promise<string>;
160
169
  export declare function discoverWorkerProjectRoot(workspaceDir: string): string;
161
170
  export declare function readWorkerTaskState(): WorkerTaskState | null;
162
171
  export declare function buildWorkerHealthAlertText(input: WorkerHealthAlertInput): string;
@@ -181,6 +190,7 @@ export declare function buildWorkerCapabilities(input: string | {
181
190
  } | null;
182
191
  maxParallelTasks?: number | null;
183
192
  runningTaskCount?: number | null;
193
+ providerAccountLabel?: string | null;
184
194
  }): AgentWorkerCapabilities;
185
195
  export declare function buildWorkerClaimBody(input: {
186
196
  workerKey: string;
@@ -254,4 +264,5 @@ export declare function readReviewEvidenceFiles(evidenceDir: string | undefined)
254
264
  contentBase64: string;
255
265
  }>;
256
266
  export declare function submitReviewTask(options: TaskSubmitReviewOptions): Promise<void>;
267
+ export declare function submitEvalTask(options: TaskSubmitEvalOptions): Promise<void>;
257
268
  export declare function failTask(options: TaskFailOptions): Promise<void>;
@@ -18,6 +18,7 @@ exports.assertTaskUploadResultMatchesContext = assertTaskUploadResultMatchesCont
18
18
  exports.stageAssignmentWorkspaceFiles = stageAssignmentWorkspaceFiles;
19
19
  exports.resolvePlaydropPluginRoot = resolvePlaydropPluginRoot;
20
20
  exports.stagePlaydropPluginReferences = stagePlaydropPluginReferences;
21
+ exports.stageAssignmentPluginBundle = stageAssignmentPluginBundle;
21
22
  exports.discoverWorkerProjectRoot = discoverWorkerProjectRoot;
22
23
  exports.readWorkerTaskState = readWorkerTaskState;
23
24
  exports.buildWorkerHealthAlertText = buildWorkerHealthAlertText;
@@ -52,6 +53,7 @@ exports.claimSlugTask = claimSlugTask;
52
53
  exports.completeTask = completeTask;
53
54
  exports.readReviewEvidenceFiles = readReviewEvidenceFiles;
54
55
  exports.submitReviewTask = submitReviewTask;
56
+ exports.submitEvalTask = submitEvalTask;
55
57
  exports.failTask = failTask;
56
58
  const promises_1 = require("node:fs/promises");
57
59
  const node_fs_1 = require("node:fs");
@@ -59,6 +61,7 @@ const node_os_1 = __importDefault(require("node:os"));
59
61
  const node_path_1 = __importDefault(require("node:path"));
60
62
  const node_process_1 = __importDefault(require("node:process"));
61
63
  const node_module_1 = require("node:module");
64
+ const node_crypto_1 = require("node:crypto");
62
65
  const fflate_1 = require("fflate");
63
66
  const types_1 = require("@playdrop/types");
64
67
  const commandContext_1 = require("../commandContext");
@@ -99,10 +102,13 @@ const FAIL_REPORT_RETRY_DELAY_MS = 2000;
99
102
  const WORKER_TRANSCRIPT_CHUNK_BATCH_SIZE = 100;
100
103
  const SLACK_API_BASE_URL = 'https://slack.com/api';
101
104
  const WORKER_WRAPPER_CONTRACT_VERSION = 1;
102
- const WORKER_SUPPORTED_KINDS = ['NEW_GAME', 'REMIX_GAME', 'GAME_UPDATE', 'GAME_REVIEW'];
105
+ const WORKER_SUPPORTED_KINDS = ['NEW_GAME', 'REMIX_GAME', 'GAME_UPDATE', 'GAME_REVIEW', 'GAME_EVAL'];
106
+ const PLAYDROP_PLUGIN_MANIFEST_REQUIRED_STARTUP_KINDS = WORKER_SUPPORTED_KINDS;
103
107
  const requireFromWorker = (0, node_module_1.createRequire)(__filename);
104
108
  const STAGED_PLAYDROP_PLUGIN_ROOT = '.playdrop/plugin';
105
109
  const PLAYDROP_PLUGIN_STAGING_MANIFEST_PATH = 'playdrop-worker-staging.json';
110
+ const ASSIGNMENT_PLUGIN_BUNDLE_MAX_FILES = 1000;
111
+ const ASSIGNMENT_PLUGIN_BUNDLE_MAX_UNCOMPRESSED_BYTES = 20 * 1024 * 1024;
106
112
  exports.WORKER_SESSION_EXPIRED_MESSAGE = 'worker session expired: run "playdrop auth login" and start the worker again';
107
113
  const WORKER_CONTEXT_ALLOWED_COMMANDS = [
108
114
  ['task', 'report'],
@@ -111,6 +117,7 @@ const WORKER_CONTEXT_ALLOWED_COMMANDS = [
111
117
  ['task', 'upload'],
112
118
  ['task', 'done'],
113
119
  ['task', 'submit-review'],
120
+ ['task', 'submit-eval'],
114
121
  ['task', 'fail'],
115
122
  ['review', 'validate-result'],
116
123
  ['review', 'compose-evidence'],
@@ -250,7 +257,7 @@ function normalizeAssignmentAgent(value) {
250
257
  return value;
251
258
  }
252
259
  function normalizeAssignmentKind(value, task) {
253
- if (value !== 'NEW_GAME' && value !== 'REMIX_GAME' && value !== 'GAME_UPDATE' && value !== 'GAME_REVIEW') {
260
+ if (value !== 'NEW_GAME' && value !== 'REMIX_GAME' && value !== 'GAME_UPDATE' && value !== 'GAME_REVIEW' && value !== 'GAME_EVAL') {
254
261
  throw new Error('agent_task_assignment_kind_missing');
255
262
  }
256
263
  if (value !== task.kind) {
@@ -310,6 +317,9 @@ function resolveWorkerClaimTaskAssignment(claim) {
310
317
  if (!version) {
311
318
  throw new Error('agent_task_assignment_output_version_missing');
312
319
  }
320
+ const pluginBundle = assignment.pluginBundle && typeof assignment.pluginBundle === 'object' && !Array.isArray(assignment.pluginBundle)
321
+ ? assignment.pluginBundle
322
+ : null;
313
323
  return {
314
324
  taskId,
315
325
  taskToken,
@@ -329,10 +339,12 @@ function resolveWorkerClaimTaskAssignment(claim) {
329
339
  baseSource: inputs.baseSource ?? null,
330
340
  remixSource: inputs.remixSource ?? null,
331
341
  reviewTarget: inputs.reviewTarget ?? null,
342
+ evalTarget: inputs.evalTarget ?? null,
332
343
  allowedTemplateKeys: Array.isArray(inputs.allowedTemplateKeys)
333
344
  ? Array.from(new Set(inputs.allowedTemplateKeys.map((value) => (typeof value === 'string' ? value.trim() : '')).filter(Boolean)))
334
345
  : [],
335
346
  },
347
+ pluginBundle,
336
348
  output: {
337
349
  appId: typeof output.appId === 'number' && Number.isInteger(output.appId) && output.appId > 0 ? output.appId : null,
338
350
  appName: typeof output.appName === 'string' && output.appName.trim() ? output.appName.trim() : null,
@@ -503,7 +515,7 @@ function readTaskContextFile(startDir = node_process_1.default.cwd()) {
503
515
  if (!Number.isInteger(taskId) || taskId <= 0
504
516
  || !Number.isInteger(attempt) || attempt <= 0
505
517
  || !taskToken
506
- || (parsed.kind !== 'NEW_GAME' && parsed.kind !== 'REMIX_GAME' && parsed.kind !== 'GAME_UPDATE' && parsed.kind !== 'GAME_REVIEW')
518
+ || (parsed.kind !== 'NEW_GAME' && parsed.kind !== 'REMIX_GAME' && parsed.kind !== 'GAME_UPDATE' && parsed.kind !== 'GAME_REVIEW' && parsed.kind !== 'GAME_EVAL')
507
519
  || (parsed.target !== 'FIRST_PARTY' && parsed.target !== 'PERSONAL')
508
520
  || !creatorUsername
509
521
  || !creatorRequest
@@ -883,8 +895,37 @@ function readPlaydropPluginStagingManifest(pluginRoot) {
883
895
  }
884
896
  const taskFiles = {};
885
897
  const rawTaskFiles = rawManifest.taskFiles;
898
+ for (const kind of PLAYDROP_PLUGIN_MANIFEST_REQUIRED_STARTUP_KINDS) {
899
+ const rawFiles = rawTaskFiles[kind];
900
+ if (!Array.isArray(rawFiles) || rawFiles.length <= 0) {
901
+ throw new Error(`playdrop_plugin_staging_manifest_incomplete:${kind}: non-empty taskFiles entry required in ${manifestPath}`);
902
+ }
903
+ const seen = new Set();
904
+ const files = rawFiles.map((value) => normalizePlaydropPluginManifestPath({ manifestPath, kind, value }));
905
+ for (const relativePath of files) {
906
+ if (seen.has(relativePath)) {
907
+ throw new Error(`playdrop_plugin_staging_manifest_duplicate_file:${kind}:${relativePath}`);
908
+ }
909
+ seen.add(relativePath);
910
+ const source = node_path_1.default.resolve(resolvedRoot, ...relativePath.split('/'));
911
+ const relativeToRoot = node_path_1.default.relative(resolvedRoot, source);
912
+ if (relativeToRoot.startsWith('..') || node_path_1.default.isAbsolute(relativeToRoot)) {
913
+ throw new Error(`playdrop_plugin_staging_manifest_invalid_path:${kind}:${relativePath}`);
914
+ }
915
+ if (!isFile(source)) {
916
+ throw new Error(`playdrop_plugin_staging_manifest_file_missing:${kind}:${relativePath}`);
917
+ }
918
+ }
919
+ taskFiles[kind] = files;
920
+ }
886
921
  for (const kind of WORKER_SUPPORTED_KINDS) {
922
+ if (taskFiles[kind]) {
923
+ continue;
924
+ }
887
925
  const rawFiles = rawTaskFiles[kind];
926
+ if (rawFiles === undefined) {
927
+ continue;
928
+ }
888
929
  if (!Array.isArray(rawFiles) || rawFiles.length <= 0) {
889
930
  throw new Error(`playdrop_plugin_staging_manifest_incomplete:${kind}: non-empty taskFiles entry required in ${manifestPath}`);
890
931
  }
@@ -908,7 +949,7 @@ function readPlaydropPluginStagingManifest(pluginRoot) {
908
949
  }
909
950
  return {
910
951
  version: 1,
911
- taskFiles,
952
+ taskFiles: taskFiles,
912
953
  };
913
954
  }
914
955
  function resolvePlaydropPluginRoot(input = {}) {
@@ -945,6 +986,9 @@ async function stagePlaydropPluginReferences(input) {
945
986
  }
946
987
  const manifest = readPlaydropPluginStagingManifest(pluginRoot);
947
988
  const referenceFiles = manifest.taskFiles[input.kind];
989
+ if (!Array.isArray(referenceFiles) || referenceFiles.length <= 0) {
990
+ throw new Error(`playdrop_plugin_staging_manifest_incomplete:${input.kind}: non-empty taskFiles entry required`);
991
+ }
948
992
  const staged = [];
949
993
  for (const relativePath of referenceFiles) {
950
994
  const destinationRelativePath = node_path_1.default.join(STAGED_PLAYDROP_PLUGIN_ROOT, relativePath);
@@ -955,6 +999,54 @@ async function stagePlaydropPluginReferences(input) {
955
999
  }
956
1000
  return staged;
957
1001
  }
1002
+ async function stageAssignmentPluginBundle(input) {
1003
+ const sha256 = typeof input.pluginBundle.sha256 === 'string' ? input.pluginBundle.sha256.trim() : '';
1004
+ const contentBase64 = typeof input.pluginBundle.contentBase64 === 'string' ? input.pluginBundle.contentBase64.trim() : '';
1005
+ if (!/^[a-f0-9]{64}$/.test(sha256) || !contentBase64) {
1006
+ throw new Error('agent_task_plugin_bundle_invalid');
1007
+ }
1008
+ const buffer = Buffer.from(contentBase64, 'base64');
1009
+ if (buffer.length <= 0) {
1010
+ throw new Error('agent_task_plugin_bundle_empty');
1011
+ }
1012
+ const actualSha = (0, node_crypto_1.createHash)('sha256').update(buffer).digest('hex');
1013
+ if (actualSha !== sha256) {
1014
+ throw new Error('agent_task_plugin_bundle_sha_mismatch');
1015
+ }
1016
+ const pluginRoot = node_path_1.default.join(input.workspaceDir, '.playdrop', 'task-plugin');
1017
+ await (0, promises_1.rm)(pluginRoot, { recursive: true, force: true });
1018
+ await (0, promises_1.mkdir)(pluginRoot, { recursive: true });
1019
+ const entries = (0, fflate_1.unzipSync)(new Uint8Array(buffer));
1020
+ const entryPairs = Object.entries(entries);
1021
+ const fileEntries = entryPairs.filter(([entryName]) => !entryName.replace(/\\/g, '/').endsWith('/'));
1022
+ if (fileEntries.length > ASSIGNMENT_PLUGIN_BUNDLE_MAX_FILES) {
1023
+ throw new Error(`agent_task_plugin_bundle_too_many_files:${fileEntries.length}>${ASSIGNMENT_PLUGIN_BUNDLE_MAX_FILES}`);
1024
+ }
1025
+ let uncompressedBytes = 0;
1026
+ for (const [entryName, content] of Object.entries(entries)) {
1027
+ const normalizedName = entryName.replace(/\\/g, '/');
1028
+ if (!normalizedName || normalizedName.startsWith('/') || normalizedName.split('/').includes('..')) {
1029
+ throw new Error(`agent_task_plugin_bundle_invalid_path:${entryName}`);
1030
+ }
1031
+ if (normalizedName.endsWith('/')) {
1032
+ await (0, promises_1.mkdir)(node_path_1.default.join(pluginRoot, normalizedName), { recursive: true });
1033
+ continue;
1034
+ }
1035
+ const destination = node_path_1.default.join(pluginRoot, normalizedName);
1036
+ const relative = node_path_1.default.relative(pluginRoot, destination);
1037
+ if (relative.startsWith('..') || node_path_1.default.isAbsolute(relative)) {
1038
+ throw new Error(`agent_task_plugin_bundle_invalid_path:${entryName}`);
1039
+ }
1040
+ uncompressedBytes += content.byteLength;
1041
+ if (uncompressedBytes > ASSIGNMENT_PLUGIN_BUNDLE_MAX_UNCOMPRESSED_BYTES) {
1042
+ throw new Error(`agent_task_plugin_bundle_too_large:${uncompressedBytes}>${ASSIGNMENT_PLUGIN_BUNDLE_MAX_UNCOMPRESSED_BYTES}`);
1043
+ }
1044
+ await (0, promises_1.mkdir)(node_path_1.default.dirname(destination), { recursive: true });
1045
+ await (0, promises_1.writeFile)(destination, Buffer.from(content));
1046
+ }
1047
+ readPlaydropPluginStagingManifest(pluginRoot);
1048
+ return pluginRoot;
1049
+ }
958
1050
  // A PlayDrop project root is the topmost directory holding a catalogue.json,
959
1051
  // the same marker "playdrop project publish" resolves its target from. Nested
960
1052
  // catalogue.json files belong to the root above them, so the walk stops at the
@@ -1316,6 +1408,7 @@ function buildWorkerCapabilities(input) {
1316
1408
  ? DEFAULT_WORKER_MAX_PARALLEL_TASKS
1317
1409
  : input.maxParallelTasks ?? DEFAULT_WORKER_MAX_PARALLEL_TASKS;
1318
1410
  const runningTaskCount = typeof input === 'string' ? 0 : input.runningTaskCount ?? 0;
1411
+ const providerAccountLabel = typeof input === 'string' ? null : input.providerAccountLabel?.trim() || null;
1319
1412
  const degradedReasons = [];
1320
1413
  const agents = [];
1321
1414
  if (codexVersion) {
@@ -1368,6 +1461,7 @@ function buildWorkerCapabilities(input) {
1368
1461
  agents,
1369
1462
  ready: agents.some((agent) => agent.ready === true),
1370
1463
  degradedReasons,
1464
+ ...(providerAccountLabel ? { providerAccountLabel } : {}),
1371
1465
  wrapperContractVersion: (0, runtime_1.readPositiveEnvInt)('PLAYDROP_WORKER_WRAPPER_CONTRACT_VERSION', WORKER_WRAPPER_CONTRACT_VERSION),
1372
1466
  ...(npmVersion ? { npmVersion } : {}),
1373
1467
  ...(playwright ? { playwright } : {}),
@@ -2170,6 +2264,7 @@ function collectWorkerLocalStatus() {
2170
2264
  playwright,
2171
2265
  runningTaskCount: 0,
2172
2266
  maxParallelTasks: (0, runtime_1.readPositiveEnvInt)('PLAYDROP_WORKER_MAX_PARALLEL_TASKS', DEFAULT_WORKER_MAX_PARALLEL_TASKS),
2267
+ providerAccountLabel: node_process_1.default.env.PLAYDROP_WORKER_AGENT_ACCOUNT_LABEL?.trim() || null,
2173
2268
  });
2174
2269
  if (pluginVersion) {
2175
2270
  capabilities.pluginVersion = pluginVersion;
@@ -3031,6 +3126,7 @@ async function startWorker(options = {}) {
3031
3126
  throw new Error('worker_session_invalid: the stored session did not resolve to a user. Run "playdrop auth login" and retry.');
3032
3127
  }
3033
3128
  const target = resolveWorkerExecutionTargetFromRole(me.user.role);
3129
+ const providerAccountLabel = readProviderAccountLabel(target);
3034
3130
  const codexVersion = probeCodexInstallation()?.codexVersion ?? null;
3035
3131
  const claudeVersion = probeClaudeInstallation()?.claudeVersion ?? null;
3036
3132
  const cursorVersion = probeCursorInstallation()?.cursorVersion ?? null;
@@ -3055,6 +3151,7 @@ async function startWorker(options = {}) {
3055
3151
  playwright,
3056
3152
  maxParallelTasks,
3057
3153
  runningTaskCount: 0,
3154
+ providerAccountLabel,
3058
3155
  });
3059
3156
  if (playdropPluginVersion) {
3060
3157
  capabilities.pluginVersion = playdropPluginVersion;
@@ -3306,7 +3403,10 @@ async function startWorker(options = {}) {
3306
3403
  message: 'Preparing worker workspace',
3307
3404
  pct: 2,
3308
3405
  });
3309
- availableSkillPaths = normalizeTelemetrySkillPaths(await stagePlaydropPluginReferences({ workspaceDir, pluginRoot: playdropPluginRoot, kind: task.kind }));
3406
+ const assignmentPluginRoot = assignment.pluginBundle
3407
+ ? await stageAssignmentPluginBundle({ workspaceDir, pluginBundle: assignment.pluginBundle })
3408
+ : playdropPluginRoot;
3409
+ availableSkillPaths = normalizeTelemetrySkillPaths(await stagePlaydropPluginReferences({ workspaceDir, pluginRoot: assignmentPluginRoot, kind: task.kind }));
3310
3410
  await client.workerCreateAgentTaskEvent(task.id, {
3311
3411
  workerKey,
3312
3412
  leaseToken,
@@ -3417,6 +3517,14 @@ async function startWorker(options = {}) {
3417
3517
  throw new Error('agent_task_assignment_review_target_missing');
3418
3518
  }
3419
3519
  }
3520
+ else if (task.kind === 'GAME_EVAL') {
3521
+ if (assignment.inputs.baseSource !== null) {
3522
+ throw new Error('agent_task_assignment_unexpected_base_source');
3523
+ }
3524
+ if (!assignment.inputs.evalTarget) {
3525
+ throw new Error('agent_task_assignment_eval_target_missing');
3526
+ }
3527
+ }
3420
3528
  else {
3421
3529
  throw new Error(`unsupported_agent_task_kind:${task.kind}`);
3422
3530
  }
@@ -3454,7 +3562,7 @@ async function startWorker(options = {}) {
3454
3562
  attempt: taskContext.attempt,
3455
3563
  devPort,
3456
3564
  claudeModel: claudeModel ?? resolveClaudeModel(assignment.model),
3457
- playdropPluginRoot,
3565
+ playdropPluginRoot: assignmentPluginRoot,
3458
3566
  onTranscriptChunks: async (chunks) => {
3459
3567
  await appendTranscriptChunks(chunks);
3460
3568
  },
@@ -3868,7 +3976,7 @@ async function resolveTaskCommandContext(command, optionsEnv, taskContext) {
3868
3976
  }
3869
3977
  async function uploadTask(options = {}) {
3870
3978
  const taskContext = readTaskContextFile();
3871
- if (taskContext.kind === 'GAME_REVIEW') {
3979
+ if (taskContext.kind === 'GAME_REVIEW' || taskContext.kind === 'GAME_EVAL') {
3872
3980
  throw new Error('task_upload_not_allowed_for_game_review');
3873
3981
  }
3874
3982
  const workspaceDir = resolveTaskWorkspaceDir();
@@ -3965,9 +4073,13 @@ async function claimSlugTask(options) {
3965
4073
  }
3966
4074
  async function completeTask(options) {
3967
4075
  const taskContext = readTaskContextFile();
3968
- if (taskContext.kind === 'GAME_REVIEW') {
4076
+ if (taskContext.kind === 'GAME_REVIEW' || taskContext.kind === 'GAME_EVAL') {
3969
4077
  throw new Error('task_done_not_allowed_for_game_review');
3970
4078
  }
4079
+ const summary = typeof options.summary === 'string' ? options.summary.trim() : '';
4080
+ if (!summary || summary.length > 200 || /[\r\n]/.test(summary)) {
4081
+ throw new Error('task_done_summary_required');
4082
+ }
3971
4083
  const ctx = await resolveTaskCommandContext('task done', options.env, taskContext);
3972
4084
  if (!ctx) {
3973
4085
  return;
@@ -4004,6 +4116,7 @@ async function completeTask(options) {
4004
4116
  creatorUsername: uploadResult.creatorUsername,
4005
4117
  completedBy: 'agent',
4006
4118
  },
4119
+ summary,
4007
4120
  ...(nextSteps !== undefined ? { nextSteps } : {}),
4008
4121
  });
4009
4122
  }
@@ -4022,7 +4135,7 @@ async function completeTask(options) {
4022
4135
  }
4023
4136
  throw error;
4024
4137
  }
4025
- (0, output_1.printSuccess)('Task marked done. Send one short final status sentence now, then stop.');
4138
+ (0, output_1.printSuccess)('Task marked done.');
4026
4139
  }
4027
4140
  function normalizeReviewSubmitState(value) {
4028
4141
  const normalized = typeof value === 'string' ? value.trim().toUpperCase() : '';
@@ -4171,6 +4284,29 @@ async function submitReviewTask(options) {
4171
4284
  });
4172
4285
  (0, output_1.printSuccess)('Review submitted. Send one short final status sentence now, then stop.');
4173
4286
  }
4287
+ async function submitEvalTask(options) {
4288
+ const taskContext = readTaskContextFile();
4289
+ if (taskContext.kind !== 'GAME_EVAL') {
4290
+ throw new Error('task_submit_eval_requires_game_eval');
4291
+ }
4292
+ const resultFile = resolveReviewFilePath(options.resultFile, 'invalid_eval_result_file');
4293
+ let result;
4294
+ try {
4295
+ result = JSON.parse((0, node_fs_1.readFileSync)(resultFile, 'utf8'));
4296
+ }
4297
+ catch (error) {
4298
+ throw new Error(`invalid_eval_result_json:${error instanceof Error ? error.message : String(error)}`);
4299
+ }
4300
+ const ctx = await resolveTaskCommandContext('task submit-eval', options.env, taskContext);
4301
+ if (!ctx) {
4302
+ throw new Error('task_submit_eval_auth_required');
4303
+ }
4304
+ await ctx.client.workerSubmitAgentTaskEval(taskContext.taskId, {
4305
+ taskToken: taskContext.taskToken,
4306
+ result: result,
4307
+ });
4308
+ (0, output_1.printSuccess)('Eval submitted. Send one short final status sentence now, then stop.');
4309
+ }
4174
4310
  async function failTask(options) {
4175
4311
  const message = options.message?.trim();
4176
4312
  if (!message) {
package/dist/index.js CHANGED
@@ -255,6 +255,7 @@ task
255
255
  task
256
256
  .command('done')
257
257
  .description('Mark the active agent task done after upload')
258
+ .requiredOption('--summary <summary>', 'One-sentence creator-facing recap of what was built')
258
259
  .option('--next-steps <path>', 'JSON file with up to three next-step suggestions')
259
260
  .option('--env <env>', 'Environment override')
260
261
  .action(async (opts) => {
@@ -272,6 +273,14 @@ task
272
273
  .action(async (opts) => {
273
274
  await (0, worker_1.submitReviewTask)(opts);
274
275
  });
276
+ task
277
+ .command('submit-eval')
278
+ .description('Submit the active game eval task result')
279
+ .requiredOption('--result-file <path>', 'Strict GAME_EVAL JSON result file')
280
+ .option('--env <env>', 'Environment override')
281
+ .action(async (opts) => {
282
+ await (0, worker_1.submitEvalTask)(opts);
283
+ });
275
284
  task
276
285
  .command('fail')
277
286
  .description('Fail the active agent task')
@@ -1040,6 +1049,7 @@ projectCapture
1040
1049
  .option('--expected-url <url>', 'Expected final URL after redirects')
1041
1050
  .option('--actions <path>', 'JSON action file with click, press, and wait steps before screenshot')
1042
1051
  .option('--viewport <size>', 'Viewport size as WIDTHxHEIGHT')
1052
+ .option('--surface <surface>', 'Browser surface preset: desktop, mobile-landscape, or mobile-portrait')
1043
1053
  .option('--fps-sample-ms <milliseconds>', 'Sample frame rate for this many milliseconds after capture')
1044
1054
  .option('--username <username>', 'Login username')
1045
1055
  .option('--password <password>', 'Login password')
@@ -1,4 +1,4 @@
1
- import type { AppleOAuthHandoffExchangeRequest, AppleOAuthHandoffExchangeResponse, AppleOAuthLinkStartRequest, AppleOAuthLinkStartResponse, ApplePushDeviceRequest, ApplePushDeviceStatusResponse, FirebasePushDeviceRequest, FirebasePushDeviceStatusResponse, ApiKeyLoginRequest, CliApiKeyStatusResponse, CliLoginApproveRequest, CliLoginApproveResponse, CliLoginPollRequest, CliLoginPollResponse, CliLoginStartResponse, CliLoginStatusResponse, CliWebLaunchStartRequest, CliWebLaunchStartResponse, CompleteXSignupRequest, CompleteXSignupResponse, DeleteMyAccountRequest, DeleteMyAccountResponse, LoginRequest, LoginResponse, LogoutResponse, PrivacyExportResponse, RegisterRequest, RegisterResponse, StarterProfileAssetsResponse, CreateAppRequest, CreateAppResponse, UpdateAppRequest, AdminUpdateAppRequest, UpdateAppResponse, AppsListResponse, AppBrowseRequest, AppDetailRequest, AppDetailResponse, AppMoreCollectionKey, AppMoreCollectionPage, AppMoreCollectionRequest, AppMoreCollectionsRequest, AppMoreCollectionsResponse, CreatorAppsBrowseRequest, AppRuntimeAssetsResponse, ContentLicense, InitializeAppUploadRequest, InitializeAppUploadResponse, UploadAppSessionFileResponse, UploadAppSessionOwnedAssetResponse, FinalizeAppUploadResponse, AppUploadLaunchCheckPreviewResponse, AbortAppUploadResponse, RecordAppUploadLaunchCheckRequest, RecordAppUploadLaunchCheckResponse, MyAppsResponse, BootstrapResponse, SetProfileAssetRequest, SetProfileAssetResponse, MeResponse, UserDetailResponse, UsersListResponse, CreateUserRequest, CreateUserResponse, UpdateAdminUserRequest, RemixScaffoldResponse, TemplateScaffoldResponse, HomeResponse, HomeCollectionPageResponse, FetchHomeOptions, DeleteAppResponse, AppType, AppAccessTokenResponse, DevAppAccessTokenResponse, DevPlayerResetResponse, AppLogEntryRequest, AppLogEntryResponse, ClaimFreeCreditRewardResponse, SubmitFeedbackRequest, SubmitFeedbackResponse, FeedbackListResponse, AdminFeedbackListResponse, AdminFeedbackResponse, UpdateAdminFeedbackRequest, UpdateAdminFeedbackResponse, DeleteFeedbackResponse, FeedbackCategory, FeedbackClient, FeedbackStatus, ShopResponse, AppleCreditPackFulfillmentRequest, AdInterstitialShowResponse, AdLoadResponse, AdShowRequest, AdRewardedShowResponse, AssetPurchaseRequest, BoostActivationRequest, BoostBalanceResponse, BoostHistoryResponse, BoostPurchaseRequest, BoostPurchaseResponse, BoostReportQuery, BoostReportResponse, BoostStatusResponse, AdLoadRequest, CreditPackCheckoutSessionRequest, PurchaseResponse, CreditPackCheckoutSessionResponse, CreditPackCheckoutStatusResponse, CreatorEarningsResponse, GoogleCreditPackFulfillmentRequest, MobileCreditPackFulfillmentResponse, TransactionsResponse, CreditPacksResponse, CreditPackResponse, PaymentProvider, PaymentStatus, AdminPaymentsListResponse, AdminPaymentDetailResponse, AdminPlatformAnalyticsRequest, AdminPlatformAnalyticsResponse, AdminRefundPaymentRequest, IapPurchaseRequest, IapPurchaseResponse, IapReceiptsResponse, IapReceiptListParams, IapReceiptResponse, AdminCreditTransactionsResponse, AiGenerationsResponse, AiGenerationDetailResponse, OwnedProfileAssetsResponse, SavedItemKind, CreateContentReportRequest, CreateCreatorReportRequest, CreateCommentReportRequest, CreatorBlockMutationResponse, LikedItemMutationResponse, DislikedItemMutationResponse, ModerationReportResponse, SavedItemMutationResponse, LibraryCategory, LibrarySort, LibraryResponse, TrackEngagementEventRequest, TrackEngagementEventResponse, CreatorFollowMutationResponse, ContentCommentsResponse, CreateContentCommentRequest, CreateContentCommentResponse, FollowingSort, FollowingCreatorsResponse, FollowingFeedSection, FollowingFeedResponse, DeleteContentCommentResponse, NotificationStatus, NotificationsResponse, NotificationReadResponse, EmailPreferencesResponse, UpdateUserCommunicationPreferencesRequest, PublicEmailPreferencesResponse, PublicEmailPreferencesUpdateRequest, EmailUnsubscribeResponse, AdminCreatorEngagementRulesResponse, AdminCreatorEngagementExecutionsResponse, AdminCreatorEngagementUserResponse, AdminCreatorEngagementRulePreviewRequest, AdminCreatorEngagementRulePreviewResponse, CreatorEngagementRuleExecutionStatus, PushSubscriptionMutationResponse, AdminUserResponse, DeleteAdminUserResponse, BatchCreateUsersResponse, UpsertWebPushSubscriptionRequest, UpdateProfileRequest, UpdateProfileResponse, WebPushConfigResponse, WebPushSubscriptionStatusResponse, ChangePasswordRequest, ChangePasswordResponse, UpgradeToCreatorResponse, AppleLinkRequest, AppleLinkResponse, AppleNativeChallengeResponse, ApplePendingSignupResponse, AppleSignInRequest, AppleSignInResponse, UnlinkXResponse, UnlinkGoogleResponse, GooglePendingSignupResponse, XPendingSignupResponse, GoogleOneTapExchangeRequest, GoogleOneTapExchangeResponse, UsernameAvailableResponse, CompleteAppleSignupRequest, CompleteAppleSignupResponse, CompleteGoogleSignupRequest, CompleteGoogleSignupResponse, GoogleAppleLinkRequest, GoogleAppleLinkResponse, GoogleAppleSignInRequest, GoogleAppleSignInResponse, AdminAppPlayerMetaResponse, AdminAppPlayerMetaUserResponse, AdminAppVersionReviewsListResponse, AdminEnqueueNextAppVersionReviewTaskResponse, AdminMutateAchievementStateRequest, AdminMutateAchievementStateResponse, AdminMutateLeaderboardScoreRequest, AdminMutateLeaderboardScoreResponse, AdminRetirePlayerMetaDefinitionResponse, AdminUpdateAppVersionReviewRequest, AdminUpdateAppVersionReviewResponse, CreateCliApiKeyResponse, GetAchievementResponse, GetLeaderboardResponse, ListAchievementsResponse, ListLeaderboardsResponse, MyAchievementsResponse, MyLeaderboardsResponse, SetAchievementProgressRequest, SetAchievementProgressResponse, SubmitLeaderboardScoreRequest, SubmitLeaderboardScoreResponse, UnlockAchievementResponse, ReviewState, AppVersionVisibility, AppVersionsListResponse, AppVersionDetailResponse, AppSourceBundleResponse, UpdateVersionResponse, DeleteVersionResponse, AdminAppsListResponse, AdminGameCollectionCandidatesResponse, AdminGameCollectionResponse, AdminGameCollectionsResponse, AdminUpdateAppResponse, CreateAdminGameCollectionRequest, DeleteAdminGameCollectionResponse, UpdateAdminGameCollectionGamesRequest, UpdateAdminGameCollectionRequest, AssetBrowseKind, AssetCategory, AssetFormat, AssetVisibility, AssetSourceKind, AssetListSort, AssetListResponse, AssetCategoriesResponse, AssetDetailResponse, AssetVersionsListResponse, CreateAssetVersionResponse, DeleteOwnedCustomAssetResponse, CreateAssetSpecVersionResponse, ListOwnedCustomAssetsResponse, LoadOwnedCustomAssetResponse, MutateOwnedCustomAssetRequest, MutateOwnedCustomAssetResponse, UpdateAssetRequest, UpdateAssetResponse, UpdateAssetVersionRequest, UpdateAssetVersionResponse, UpdateAssetSpecVersionResponse, DeleteAssetVersionResponse, DeleteAssetResponse, DeleteAssetSpecVersionResponse, DeleteAssetSpecResponse, AssetSourceBundleResponse, AssetPackListSort, AssetSpecAssetsListResponse, AssetSpecAppsListResponse, AssetSpecDetailResponse, AssetSpecListSort, AssetSpecListResponse, AssetSpecVersionResponseEnvelope, AssetSpecVersionsListResponse, AssetPackSourceBundleResponse, AssetPackListResponse, AssetPackDetailResponse, AssetPackVersionsListResponse, InitializeAssetPackUploadRequest, InitializeAssetPackUploadResponse, UploadAssetPackSessionAssetResponse, UploadAssetPackSessionMediaResponse, FinalizeAssetPackUploadResponse, AbortAssetPackUploadResponse, UpdateAssetPackRequest, UpdateAssetPackResponse, UpdateAssetPackVersionRequest, UpdateAssetPackVersionResponse, DeleteAssetPackVersionResponse, DeleteAssetPackResponse, BatchUpsertNodeRelationsRequest, BatchUpsertNodeRelationsResponse, ContentRemixRelationsResponse, SearchRequest, SearchResponse, SearchSuggestRequest, SearchSuggestResponse, AdminTagGroupResponse, AdminTagGroupsResponse, AdminTagResponse, CreateTagGroupRequest, CreateTagRequest, TagDirectoryResponse, TagDetailResponse, TagGroupDetailResponse, TagGroupSort, TagListResponse, UpdateTagGroupRequest, UpdateTagRequest, AdminAgentTaskDetailResponse, AdminAgentTaskTranscriptResponse, AdminAgentTasksResponse, AdminAgentWorkersStatusResponse, AgentTaskAvailabilityResponse, AgentTaskAttachmentUploadResponse, AgentTaskCreatorFeedbackStatus, AgentTaskDetailResponse, AgentTaskEventsResponse, AgentTaskKind, AgentTaskNewGameSuggestionsResponse, AgentTasksResponse, AppAgentTaskResponse, CancelAgentTaskResponse, ClearAgentTaskResponse, CreateAppAgentTaskRequest, CreateAppAgentTaskResponse, CreateNewGameAgentTaskRequest, CreateNewGameAgentTaskResponse, CreateRemixGameAgentTaskRequest, CreateRemixGameAgentTaskResponse, CreatorGameCreatorFeedbackStatusResponse, CreatorGamesListResponse, CreatorGameShareResponse, CreatorGameStatusResponse, CreatorGameVersionsResponse, MeAgentWorkersResponse, RetryAgentTaskResponse, WorkerClaimAgentTaskRequest, WorkerClaimAgentTaskResponse, WorkerClaimAgentTaskSlugRequest, WorkerClaimAgentTaskSlugResponse, WorkerCompleteAgentTaskRequest, WorkerCreateAgentTaskEventRequest, WorkerCreateAgentTaskEventResponse, WorkerCreateAgentTaskTranscriptChunkRequest, WorkerCreateAgentTaskTranscriptChunkResponse, WorkerAgentTaskAttemptUnavailableRequest, WorkerAgentTaskAttemptUnavailableResponse, WorkerFailAgentTaskRequest, WorkerHeartbeatAgentTaskRequest, WorkerHeartbeatAgentTaskResponse, WorkerRecordAgentTaskRunTelemetryRequest, WorkerRecordAgentTaskRunTelemetryResponse, WorkerPresenceRequest, WorkerPresenceResponse, WorkerSubmitAgentTaskReviewRequest, WorkerSubmitAgentTaskReviewResponse, WorkerUpdateIntentRequest, WorkerUpdateIntentResponse, FreeCreditsResponse, InvitePreviewResponse, MyInviteCodeResponse } from '@playdrop/types';
1
+ import type { AppleOAuthHandoffExchangeRequest, AppleOAuthHandoffExchangeResponse, AppleOAuthLinkStartRequest, AppleOAuthLinkStartResponse, ApplePushDeviceRequest, ApplePushDeviceStatusResponse, FirebasePushDeviceRequest, FirebasePushDeviceStatusResponse, ApiKeyLoginRequest, CliApiKeyStatusResponse, CliLoginApproveRequest, CliLoginApproveResponse, CliLoginPollRequest, CliLoginPollResponse, CliLoginStartResponse, CliLoginStatusResponse, CliWebLaunchStartRequest, CliWebLaunchStartResponse, CompleteXSignupRequest, CompleteXSignupResponse, DeleteMyAccountRequest, DeleteMyAccountResponse, LoginRequest, LoginResponse, LogoutResponse, PrivacyExportResponse, RegisterRequest, RegisterResponse, StarterProfileAssetsResponse, CreateAppRequest, CreateAppResponse, UpdateAppRequest, AdminUpdateAppRequest, UpdateAppResponse, AppsListResponse, AppBrowseRequest, AppDetailRequest, AppDetailResponse, AppMoreCollectionKey, AppMoreCollectionPage, AppMoreCollectionRequest, AppMoreCollectionsRequest, AppMoreCollectionsResponse, CreatorAppsBrowseRequest, AppRuntimeAssetsResponse, ContentLicense, InitializeAppUploadRequest, InitializeAppUploadResponse, UploadAppSessionFileResponse, UploadAppSessionOwnedAssetResponse, FinalizeAppUploadResponse, AppUploadLaunchCheckPreviewResponse, AbortAppUploadResponse, RecordAppUploadLaunchCheckRequest, RecordAppUploadLaunchCheckResponse, MyAppsResponse, BootstrapResponse, SetProfileAssetRequest, SetProfileAssetResponse, MeResponse, UserDetailResponse, UsersListResponse, CreateUserRequest, CreateUserResponse, UpdateAdminUserRequest, RemixScaffoldResponse, TemplateScaffoldResponse, HomeResponse, HomeCollectionPageResponse, FetchHomeOptions, DeleteAppResponse, AppType, AppAccessTokenResponse, DevAppAccessTokenResponse, DevPlayerResetResponse, AppLogEntryRequest, AppLogEntryResponse, ClaimFreeCreditRewardResponse, SubmitFeedbackRequest, SubmitFeedbackResponse, FeedbackListResponse, AdminFeedbackListResponse, AdminFeedbackResponse, UpdateAdminFeedbackRequest, UpdateAdminFeedbackResponse, DeleteFeedbackResponse, FeedbackCategory, FeedbackClient, FeedbackStatus, ShopResponse, AppleCreditPackFulfillmentRequest, AdInterstitialShowResponse, AdLoadResponse, AdShowRequest, AdRewardedShowResponse, AssetPurchaseRequest, BoostActivationRequest, BoostBalanceResponse, BoostHistoryResponse, BoostPurchaseRequest, BoostPurchaseResponse, BoostReportQuery, BoostReportResponse, BoostStatusResponse, AdLoadRequest, CreditPackCheckoutSessionRequest, PurchaseResponse, CreditPackCheckoutSessionResponse, CreditPackCheckoutStatusResponse, CreatorEarningsResponse, GoogleCreditPackFulfillmentRequest, MobileCreditPackFulfillmentResponse, TransactionsResponse, CreditPacksResponse, CreditPackResponse, PaymentProvider, PaymentStatus, AdminPaymentsListResponse, AdminPaymentDetailResponse, AdminPlatformAnalyticsRequest, AdminPlatformAnalyticsResponse, AdminRefundPaymentRequest, IapPurchaseRequest, IapPurchaseResponse, IapReceiptsResponse, IapReceiptListParams, IapReceiptResponse, AdminCreditTransactionsResponse, AiGenerationsResponse, AiGenerationDetailResponse, OwnedProfileAssetsResponse, SavedItemKind, CreateContentReportRequest, CreateCreatorReportRequest, CreateCommentReportRequest, CreatorBlockMutationResponse, LikedItemMutationResponse, DislikedItemMutationResponse, ModerationReportResponse, SavedItemMutationResponse, LibraryCategory, LibrarySort, LibraryResponse, TrackEngagementEventRequest, TrackEngagementEventResponse, CreatorFollowMutationResponse, ContentCommentsResponse, CreateContentCommentRequest, CreateContentCommentResponse, FollowingSort, FollowingCreatorsResponse, FollowingFeedSection, FollowingFeedResponse, DeleteContentCommentResponse, NotificationStatus, NotificationsResponse, NotificationReadResponse, EmailPreferencesResponse, UpdateUserCommunicationPreferencesRequest, PublicEmailPreferencesResponse, PublicEmailPreferencesUpdateRequest, EmailUnsubscribeResponse, AdminCreatorEngagementRulesResponse, AdminCreatorEngagementExecutionsResponse, AdminCreatorEngagementUserResponse, AdminCreatorEngagementRulePreviewRequest, AdminCreatorEngagementRulePreviewResponse, CreatorEngagementRuleExecutionStatus, PushSubscriptionMutationResponse, AdminUserResponse, DeleteAdminUserResponse, BatchCreateUsersResponse, UpsertWebPushSubscriptionRequest, UpdateProfileRequest, UpdateProfileResponse, WebPushConfigResponse, WebPushSubscriptionStatusResponse, ChangePasswordRequest, ChangePasswordResponse, UpgradeToCreatorResponse, AppleLinkRequest, AppleLinkResponse, AppleNativeChallengeResponse, ApplePendingSignupResponse, AppleSignInRequest, AppleSignInResponse, UnlinkXResponse, UnlinkGoogleResponse, GooglePendingSignupResponse, XPendingSignupResponse, GoogleOneTapExchangeRequest, GoogleOneTapExchangeResponse, UsernameAvailableResponse, CompleteAppleSignupRequest, CompleteAppleSignupResponse, CompleteGoogleSignupRequest, CompleteGoogleSignupResponse, GoogleAppleLinkRequest, GoogleAppleLinkResponse, GoogleAppleSignInRequest, GoogleAppleSignInResponse, AdminAppPlayerMetaResponse, AdminAppPlayerMetaUserResponse, AdminAppVersionReviewsListResponse, AdminEnqueueNextAppVersionReviewTaskResponse, AdminMutateAchievementStateRequest, AdminMutateAchievementStateResponse, AdminMutateLeaderboardScoreRequest, AdminMutateLeaderboardScoreResponse, AdminRetirePlayerMetaDefinitionResponse, AdminUpdateAppVersionReviewRequest, AdminUpdateAppVersionReviewResponse, CreateCliApiKeyResponse, GetAchievementResponse, GetLeaderboardResponse, ListAchievementsResponse, ListLeaderboardsResponse, MyAchievementsResponse, MyLeaderboardsResponse, SetAchievementProgressRequest, SetAchievementProgressResponse, SubmitLeaderboardScoreRequest, SubmitLeaderboardScoreResponse, UnlockAchievementResponse, ReviewState, AppVersionVisibility, AppVersionsListResponse, AppVersionDetailResponse, AppSourceBundleResponse, UpdateVersionResponse, DeleteVersionResponse, AdminAppsListResponse, AdminGameCollectionCandidatesResponse, AdminGameCollectionResponse, AdminGameCollectionsResponse, AdminUpdateAppResponse, CreateAdminGameCollectionRequest, DeleteAdminGameCollectionResponse, UpdateAdminGameCollectionGamesRequest, UpdateAdminGameCollectionRequest, AssetBrowseKind, AssetCategory, AssetFormat, AssetVisibility, AssetSourceKind, AssetListSort, AssetListResponse, AssetCategoriesResponse, AssetDetailResponse, AssetVersionsListResponse, CreateAssetVersionResponse, DeleteOwnedCustomAssetResponse, CreateAssetSpecVersionResponse, ListOwnedCustomAssetsResponse, LoadOwnedCustomAssetResponse, MutateOwnedCustomAssetRequest, MutateOwnedCustomAssetResponse, UpdateAssetRequest, UpdateAssetResponse, UpdateAssetVersionRequest, UpdateAssetVersionResponse, UpdateAssetSpecVersionResponse, DeleteAssetVersionResponse, DeleteAssetResponse, DeleteAssetSpecVersionResponse, DeleteAssetSpecResponse, AssetSourceBundleResponse, AssetPackListSort, AssetSpecAssetsListResponse, AssetSpecAppsListResponse, AssetSpecDetailResponse, AssetSpecListSort, AssetSpecListResponse, AssetSpecVersionResponseEnvelope, AssetSpecVersionsListResponse, AssetPackSourceBundleResponse, AssetPackListResponse, AssetPackDetailResponse, AssetPackVersionsListResponse, InitializeAssetPackUploadRequest, InitializeAssetPackUploadResponse, UploadAssetPackSessionAssetResponse, UploadAssetPackSessionMediaResponse, FinalizeAssetPackUploadResponse, AbortAssetPackUploadResponse, UpdateAssetPackRequest, UpdateAssetPackResponse, UpdateAssetPackVersionRequest, UpdateAssetPackVersionResponse, DeleteAssetPackVersionResponse, DeleteAssetPackResponse, BatchUpsertNodeRelationsRequest, BatchUpsertNodeRelationsResponse, ContentRemixRelationsResponse, SearchRequest, SearchResponse, SearchSuggestRequest, SearchSuggestResponse, AdminTagGroupResponse, AdminTagGroupsResponse, AdminTagResponse, CreateTagGroupRequest, CreateTagRequest, TagDirectoryResponse, TagDetailResponse, TagGroupDetailResponse, TagGroupSort, TagListResponse, UpdateTagGroupRequest, UpdateTagRequest, AdminAgentTaskDetailResponse, AdminAgentTaskTranscriptResponse, AdminAgentTasksResponse, AdminAgentWorkersStatusResponse, AgentTaskAvailabilityResponse, AgentTaskAttachmentUploadResponse, AgentTaskCreatorFeedbackStatus, AgentTaskDetailResponse, AgentTaskEventsResponse, AgentTaskKind, AgentTaskNewGameSuggestionsResponse, AgentTasksResponse, AppAgentTaskResponse, CancelAgentTaskResponse, ClearAgentTaskResponse, CreateAppAgentTaskRequest, CreateAppAgentTaskResponse, CreateGameEvalAgentTaskRequest, CreateGameEvalAgentTaskResponse, CreateNewGameAgentTaskRequest, CreateNewGameAgentTaskResponse, CreateRemixGameAgentTaskRequest, CreateRemixGameAgentTaskResponse, CreatorGameCreatorFeedbackStatusResponse, CreatorGamesListResponse, CreatorGameShareResponse, CreatorGameStatusResponse, CreatorGameVersionsResponse, MeAgentWorkersResponse, RetryAgentTaskResponse, WorkerClaimAgentTaskRequest, WorkerClaimAgentTaskResponse, WorkerClaimAgentTaskSlugRequest, WorkerClaimAgentTaskSlugResponse, WorkerCompleteAgentTaskRequest, WorkerCreateAgentTaskEventRequest, WorkerCreateAgentTaskEventResponse, WorkerCreateAgentTaskTranscriptChunkRequest, WorkerCreateAgentTaskTranscriptChunkResponse, WorkerAgentTaskAttemptUnavailableRequest, WorkerAgentTaskAttemptUnavailableResponse, WorkerFailAgentTaskRequest, WorkerHeartbeatAgentTaskRequest, WorkerHeartbeatAgentTaskResponse, WorkerRecordAgentTaskRunTelemetryRequest, WorkerRecordAgentTaskRunTelemetryResponse, WorkerPresenceRequest, WorkerPresenceResponse, WorkerSubmitAgentTaskEvalRequest, WorkerSubmitAgentTaskEvalResponse, WorkerSubmitAgentTaskReviewRequest, WorkerSubmitAgentTaskReviewResponse, WorkerUpdateIntentRequest, WorkerUpdateIntentResponse, FreeCreditsResponse, InvitePreviewResponse, MyInviteCodeResponse } from '@playdrop/types';
2
2
  import { type AdminAgentTaskTranscriptOptions, type ListCreatorGamesOptions, type ListAgentTasksOptions } from './domains/agent-tasks.js';
3
3
  export interface HttpMethod {
4
4
  GET: 'GET';
@@ -135,6 +135,7 @@ export interface ApiClient {
135
135
  uploadAgentTaskAttachment(file: Blob, description?: string, filename?: string): Promise<AgentTaskAttachmentUploadResponse>;
136
136
  createNewGameAgentTask(body: CreateNewGameAgentTaskRequest): Promise<CreateNewGameAgentTaskResponse>;
137
137
  createRemixGameAgentTask(body: CreateRemixGameAgentTaskRequest): Promise<CreateRemixGameAgentTaskResponse>;
138
+ createGameEvalAgentTask(body: CreateGameEvalAgentTaskRequest): Promise<CreateGameEvalAgentTaskResponse>;
138
139
  createAppAgentTask(appName: string, body: CreateAppAgentTaskRequest): Promise<CreateAppAgentTaskResponse>;
139
140
  getAppAgentTask(appName: string): Promise<AppAgentTaskResponse>;
140
141
  getAppAgentTaskAvailability(appName: string): Promise<AgentTaskAvailabilityResponse>;
@@ -163,6 +164,7 @@ export interface ApiClient {
163
164
  workerRecordAgentTaskRunTelemetry(taskId: number, body: WorkerRecordAgentTaskRunTelemetryRequest): Promise<WorkerRecordAgentTaskRunTelemetryResponse>;
164
165
  workerCompleteAgentTask(taskId: number, body: WorkerCompleteAgentTaskRequest): Promise<AgentTaskDetailResponse>;
165
166
  workerSubmitAgentTaskReview(taskId: number, body: WorkerSubmitAgentTaskReviewRequest): Promise<WorkerSubmitAgentTaskReviewResponse>;
167
+ workerSubmitAgentTaskEval(taskId: number, body: WorkerSubmitAgentTaskEvalRequest): Promise<WorkerSubmitAgentTaskEvalResponse>;
166
168
  workerFailAgentTask(taskId: number, body: WorkerFailAgentTaskRequest): Promise<AgentTaskDetailResponse>;
167
169
  adminListAgentTasks(options?: ListAgentTasksOptions): Promise<AdminAgentTasksResponse>;
168
170
  adminGetAgentTask(taskId: number): Promise<AdminAgentTaskDetailResponse>;