@farmslot/agent-runtime 0.18.1 → 0.19.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 CHANGED
@@ -2,6 +2,14 @@
2
2
 
3
3
  ## Unreleased
4
4
 
5
+ - Active-development baseline; add user-facing changes here before release or package publication.
6
+
7
+ ## 0.19.0 - 2026-10-13
8
+
9
+ - Validate the current retained recipe attempt selected by the task pointer while keeping earlier packages intact.
10
+ - Resolve declared execution-template sources through an attested source binding.
11
+ - Accept the reviewer feedback path binding in template lint while retaining the required feedback artifact check.
12
+
5
13
  ## 0.18.1 - 2026-10-12
6
14
 
7
15
  - Update shared runtime dependencies for bounded recipe log observations.
@@ -1,4 +1,4 @@
1
- import type { ProjectExecutionTemplatesConfig, UnavailableExecutionTemplateSource } from '@farmslot/protocol';
1
+ import type { ProjectExecutionTemplatesConfig, SourceEntryRef, UnavailableExecutionTemplateSource } from '@farmslot/protocol';
2
2
  import type { ExecutionTemplateSource } from './types.js';
3
3
  export type { UnavailableExecutionTemplateSource } from '@farmslot/protocol';
4
4
  export interface ResolvedExecutionTemplateSources {
@@ -6,6 +6,11 @@ export interface ResolvedExecutionTemplateSources {
6
6
  unavailable: UnavailableExecutionTemplateSource[];
7
7
  }
8
8
  export interface ResolveConfiguredExecutionTemplateSourcesOptions {
9
+ resolveSourceBinding?: (selection: SourceEntryRef) => {
10
+ root: string;
11
+ commit: string;
12
+ lockDigest: string;
13
+ };
9
14
  projectPackRoot: string;
10
15
  env?: NodeJS.ProcessEnv;
11
16
  }
@@ -1 +1 @@
1
- {"version":3,"file":"source-config.d.ts","sourceRoot":"","sources":["../../src/execution-template/source-config.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAEV,+BAA+B,EAC/B,kCAAkC,EACnC,MAAM,oBAAoB,CAAC;AAE5B,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,YAAY,CAAC;AAE1D,YAAY,EAAE,kCAAkC,EAAE,MAAM,oBAAoB,CAAC;AAE7E,MAAM,WAAW,gCAAgC;IAC/C,OAAO,EAAE,uBAAuB,EAAE,CAAC;IACnC,WAAW,EAAE,kCAAkC,EAAE,CAAC;CACnD;AAED,MAAM,WAAW,gDAAgD;IAC/D,eAAe,EAAE,MAAM,CAAC;IACxB,GAAG,CAAC,EAAE,MAAM,CAAC,UAAU,CAAC;CACzB;AAUD,wBAAgB,+BAA+B,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,CAQhF;AAED,wBAAgB,4BAA4B,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,GAAG,SAAS,CAO9E;AAeD;;;GAGG;AACH,wBAAgB,yCAAyC,CACvD,MAAM,EAAE,+BAA+B,GAAG,SAAS,EACnD,OAAO,EAAE,gDAAgD,GACxD,gCAAgC,CAoDlC"}
1
+ {"version":3,"file":"source-config.d.ts","sourceRoot":"","sources":["../../src/execution-template/source-config.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAEV,+BAA+B,EAC/B,cAAc,EACd,kCAAkC,EACnC,MAAM,oBAAoB,CAAC;AAE5B,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,YAAY,CAAC;AAE1D,YAAY,EAAE,kCAAkC,EAAE,MAAM,oBAAoB,CAAC;AAE7E,MAAM,WAAW,gCAAgC;IAC/C,OAAO,EAAE,uBAAuB,EAAE,CAAC;IACnC,WAAW,EAAE,kCAAkC,EAAE,CAAC;CACnD;AAED,MAAM,WAAW,gDAAgD;IAC/D,oBAAoB,CAAC,EAAE,CAAC,SAAS,EAAE,cAAc,KAAK;QACpD,IAAI,EAAE,MAAM,CAAC;QACb,MAAM,EAAE,MAAM,CAAC;QACf,UAAU,EAAE,MAAM,CAAC;KACpB,CAAC;IACF,eAAe,EAAE,MAAM,CAAC;IACxB,GAAG,CAAC,EAAE,MAAM,CAAC,UAAU,CAAC;CACzB;AAUD,wBAAgB,+BAA+B,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,CAQhF;AAED,wBAAgB,4BAA4B,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,GAAG,SAAS,CAO9E;AA2BD;;;GAGG;AACH,wBAAgB,yCAAyC,CACvD,MAAM,EAAE,+BAA+B,GAAG,SAAS,EACnD,OAAO,EAAE,gDAAgD,GACxD,gCAAgC,CAoDlC"}
@@ -26,7 +26,19 @@ export function executionTemplateSourceDirty(root) {
26
26
  return result.stdout.trim().length > 0;
27
27
  }
28
28
  function configuredRoot(source, options) {
29
+ if (source.root.sourceId) {
30
+ if (!options.resolveSourceBinding)
31
+ return { reason: 'invalid-root' };
32
+ return {
33
+ path: options.resolveSourceBinding({
34
+ sourceId: source.root.sourceId,
35
+ entry: source.root.entry,
36
+ }).root,
37
+ };
38
+ }
29
39
  if (typeof source.root.env === 'string') {
40
+ if (options.resolveSourceBinding)
41
+ return { reason: 'invalid-root' };
30
42
  const value = (options.env ?? process.env)[source.root.env]?.trim();
31
43
  if (!value)
32
44
  return { reason: 'missing-environment' };
@@ -34,7 +46,9 @@ function configuredRoot(source, options) {
34
46
  return { reason: 'invalid-root' };
35
47
  return { path: value };
36
48
  }
37
- return { path: path.resolve(options.projectPackRoot, source.root.projectPath) };
49
+ return source.root.projectPath
50
+ ? { path: path.resolve(options.projectPackRoot, source.root.projectPath) }
51
+ : { reason: 'invalid-root' };
38
52
  }
39
53
  /**
40
54
  * Resolve optional configured sources only when catalog options are requested.
@@ -1 +1 @@
1
- {"version":3,"file":"source-config.js","sourceRoot":"","sources":["../../src/execution-template/source-config.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"source-config.js","sourceRoot":"","sources":["../../src/execution-template/source-config.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@farmslot/agent-runtime",
3
- "version": "0.18.1",
3
+ "version": "0.19.0",
4
4
  "type": "module",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",
@@ -21,6 +21,10 @@
21
21
  "./scripts/subtask-unit.cjs": "./scripts/subtask-unit.cjs",
22
22
  "./scripts/worker-terminal-contract.cjs": "./scripts/worker-terminal-contract.cjs",
23
23
  "./scripts/check-task-artifact-contract.mjs": "./scripts/check-task-artifact-contract.mjs",
24
+ "./scripts/retained-recipe-attempt.cjs": {
25
+ "types": "./scripts/retained-recipe-attempt.d.cts",
26
+ "default": "./scripts/retained-recipe-attempt.cjs"
27
+ },
24
28
  "./scripts/execution-template-cli.mjs": "./scripts/execution-template-cli.mjs",
25
29
  "./scripts/task-init-cli.mjs": "./scripts/task-init-cli.mjs",
26
30
  "./native": {
@@ -45,7 +49,7 @@
45
49
  "prepublishOnly": "node ../../scripts/quality/check-farmslot-package-readiness.mjs --publish --packages @farmslot/agent-runtime"
46
50
  },
47
51
  "dependencies": {
48
- "@farmslot/protocol": "0.40.0"
52
+ "@farmslot/protocol": "0.41.0"
49
53
  },
50
54
  "devDependencies": {
51
55
  "@types/node": "^22.0.0",
@@ -82,6 +86,7 @@
82
86
  "dist/**/*.js.map",
83
87
  "scripts/**/*.cjs",
84
88
  "scripts/**/*.mjs",
89
+ "scripts/retained-recipe-attempt.d.cts",
85
90
  "scripts/execution-template-cli.mjs"
86
91
  ],
87
92
  "publishConfig": {
@@ -324,14 +324,28 @@ function validateRecipeDocumentArtifact() {
324
324
  if (authoredRecipe === undefined) return;
325
325
  validateRecipeDocumentValue(authoredRecipe, 'recipe.json', { skipRecipeCallResolution: true });
326
326
 
327
- const packageRoot = 'artifacts/recipe-run';
327
+ let packageRoot = 'artifacts/recipe-run';
328
+ const pointerValue = readJsonArtifact(
329
+ 'artifacts/latest-valid-recipe-run.json',
330
+ 'latest-valid-recipe-run.json',
331
+ );
332
+ if (pointerValue !== undefined) {
333
+ const pointer = recipeProtocol?.sanitizeLatestValidRecipeRunPointer?.(pointerValue);
334
+ if (!pointer) {
335
+ issues.push(
336
+ 'latest-valid-recipe-run.json: invalid pointer or current @farmslot/protocol is unavailable',
337
+ );
338
+ return;
339
+ }
340
+ packageRoot = `artifacts/${pointer.relativeArtifactRoot}`;
341
+ }
328
342
  const recipe = readJsonArtifact(`${packageRoot}/recipe.json`, 'recipe-run/recipe.json');
329
343
  if (recipe === undefined) {
330
- issues.push('artifacts/recipe-run/recipe.json is missing');
344
+ issues.push(`${packageRoot}/recipe.json is missing`);
331
345
  return;
332
346
  }
333
347
  if (canonicalJson(authoredRecipe) !== canonicalJson(recipe)) {
334
- issues.push('artifacts/recipe-run/recipe.json does not match artifacts/recipe.json');
348
+ issues.push(`${packageRoot}/recipe.json does not match artifacts/recipe.json`);
335
349
  }
336
350
  const manifest = readJsonArtifact(
337
351
  `${packageRoot}/artifact-manifest.json`,
@@ -0,0 +1,48 @@
1
+ 'use strict';
2
+
3
+ const { randomUUID } = require('node:crypto');
4
+ const {
5
+ existsSync,
6
+ readFileSync,
7
+ realpathSync,
8
+ renameSync,
9
+ rmSync,
10
+ writeFileSync,
11
+ } = require('node:fs');
12
+ const path = require('node:path');
13
+ const { sanitizeLatestValidRecipeRunPointer } = require('@farmslot/protocol/recipe');
14
+
15
+ /** Advance task selection after success without changing any attempt bytes. */
16
+ function recordRecipeAttemptSelection(taskDir, artifactDir) {
17
+ const artifacts = realpathSync(path.join(taskDir, 'artifacts'));
18
+ const attempt = realpathSync(artifactDir);
19
+ const relative = path.relative(artifacts, attempt).split(path.sep).join('/');
20
+ const pointer = sanitizeLatestValidRecipeRunPointer({
21
+ version: 1,
22
+ relativeArtifactRoot: relative,
23
+ updatedAt: new Date().toISOString(),
24
+ });
25
+ if (!pointer) return false;
26
+ const summary = JSON.parse(readFileSync(path.join(attempt, 'summary.json'), 'utf8'));
27
+ if (summary.status !== 'pass') return false;
28
+ const destination = path.join(artifacts, 'latest-valid-recipe-run.json');
29
+ const temporary = `${destination}.${randomUUID()}.tmp`;
30
+ try {
31
+ writeFileSync(temporary, `${JSON.stringify(pointer)}\n`, { flag: 'wx', mode: 0o600 });
32
+ renameSync(temporary, destination);
33
+ } finally {
34
+ rmSync(temporary, { force: true });
35
+ }
36
+ return true;
37
+ }
38
+
39
+ function readRecipeAttemptSelection(taskDir) {
40
+ const file = path.join(taskDir, 'artifacts', 'latest-valid-recipe-run.json');
41
+ if (!existsSync(file)) return null;
42
+ const pointer = sanitizeLatestValidRecipeRunPointer(JSON.parse(readFileSync(file, 'utf8')));
43
+ if (!pointer) throw new Error('Invalid retained recipe attempt selection.');
44
+ return pointer;
45
+ }
46
+
47
+ module.exports = { readRecipeAttemptSelection, recordRecipeAttemptSelection };
48
+ if (require.main === module) recordRecipeAttemptSelection(process.argv[2], process.argv[3]);
@@ -0,0 +1,4 @@
1
+ import type { LatestValidRecipeRunPointer } from '@farmslot/protocol/recipe';
2
+
3
+ export function readRecipeAttemptSelection(taskDir: string): LatestValidRecipeRunPointer | null;
4
+ export function recordRecipeAttemptSelection(taskDir: string, artifactDir: string): boolean;
@@ -391,7 +391,10 @@ function lintWorkerTemplateAgainstContract(templateContent, contract) {
391
391
  const spec = contract.commands[/** @type {WorkerTerminalCommand} */ (command)];
392
392
  if (!spec) continue;
393
393
  for (const artifactPath of spec.artifacts) {
394
- if (!templateContent.includes(artifactPath)) {
394
+ const reviewerFeedbackBinding =
395
+ artifactPath === 'artifacts/review-feedback.md' &&
396
+ templateContent.includes('{{REVIEW_FEEDBACK}}');
397
+ if (!templateContent.includes(artifactPath) && !reviewerFeedbackBinding) {
395
398
  issues.push(
396
399
  `missing checklist/reference to required artifact \`${artifactPath}\` for \`${command}\``,
397
400
  );