ocpipe 0.3.8 → 0.3.9

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/README.md CHANGED
@@ -49,6 +49,13 @@ type GreetOut = InferOutputs<typeof Greet> // { greeting: string }
49
49
 
50
50
  OpenCode CLI is bundled — run `bun run opencode` or use your system `opencode` if installed.
51
51
 
52
+ ### Requirements
53
+
54
+ Currently requires [this OpenCode fork](https://github.com/paralin/opencode). Once the following PRs are merged, the official release will work:
55
+
56
+ - [#5426](https://github.com/anomalyco/opencode/pull/5426) - Adds `--prompt-file` flag
57
+ - [#5339](https://github.com/anomalyco/opencode/pull/5339) - Session export fixes
58
+
52
59
  ### Documentation
53
60
 
54
61
  - [Getting Started](./GETTING_STARTED.md) - Tutorial with examples
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "ocpipe",
3
- "version": "0.3.8",
3
+ "version": "0.3.9",
4
4
  "description": "SDK for LLM pipelines with OpenCode and Zod",
5
5
  "type": "module",
6
6
  "main": "src/index.ts",
package/src/agent.ts CHANGED
@@ -6,7 +6,7 @@
6
6
 
7
7
  import { spawn } from 'child_process'
8
8
  import { existsSync } from 'fs'
9
- import { mkdir } from 'fs/promises'
9
+ import { mkdir, writeFile, unlink } from 'fs/promises'
10
10
  import { join } from 'path'
11
11
  import { PROJECT_ROOT, TMP_DIR } from './paths.js'
12
12
  import type { RunAgentOptions, RunAgentResult } from './types.js'
@@ -60,6 +60,13 @@ export async function runAgent(
60
60
  `\n>>> OpenCode [${agent}] [${modelStr}] ${sessionInfo}: ${promptPreview}...`,
61
61
  )
62
62
 
63
+ // Write prompt to .opencode/prompts/ within the working directory
64
+ const cwd = workdir ?? PROJECT_ROOT
65
+ const promptsDir = join(cwd, '.opencode', 'prompts')
66
+ await mkdir(promptsDir, { recursive: true })
67
+ const promptFile = join(promptsDir, `prompt_${Date.now()}.txt`)
68
+ await writeFile(promptFile, prompt)
69
+
63
70
  const args = [
64
71
  'run',
65
72
  '--format',
@@ -68,19 +75,18 @@ export async function runAgent(
68
75
  agent,
69
76
  '--model',
70
77
  modelStr,
78
+ '--prompt-file',
79
+ promptFile,
71
80
  ]
72
81
 
73
82
  if (sessionId) {
74
83
  args.push('--session', sessionId)
75
84
  }
76
85
 
77
- // Pass prompt as positional argument (stdin doesn't work without TTY)
78
- args.push(prompt)
79
-
80
86
  return new Promise((resolve, reject) => {
81
87
  const opencodeCmd = getOpencodeCommand(args)
82
88
  const proc = spawn(opencodeCmd.cmd, opencodeCmd.args, {
83
- cwd: workdir ?? PROJECT_ROOT,
89
+ cwd,
84
90
  stdio: ['ignore', 'pipe', 'pipe'],
85
91
  })
86
92
 
@@ -118,8 +124,9 @@ export async function runAgent(
118
124
  // Timeout handling (0 = no timeout)
119
125
  const timeout =
120
126
  timeoutSec > 0 ?
121
- setTimeout(() => {
127
+ setTimeout(async () => {
122
128
  proc.kill()
129
+ await unlink(promptFile).catch(() => {})
123
130
  reject(new Error(`Timeout after ${timeoutSec}s`))
124
131
  }, timeoutSec * 1000)
125
132
  : null
@@ -127,6 +134,9 @@ export async function runAgent(
127
134
  proc.on('close', async (code) => {
128
135
  if (timeout) clearTimeout(timeout)
129
136
 
137
+ // Clean up prompt file
138
+ await unlink(promptFile).catch(() => {})
139
+
130
140
  if (code !== 0) {
131
141
  const stderr = stderrChunks.join('').trim()
132
142
  const lastLines = stderr.split('\n').slice(-5).join('\n')
@@ -156,8 +166,9 @@ export async function runAgent(
156
166
  })
157
167
  })
158
168
 
159
- proc.on('error', (err) => {
169
+ proc.on('error', async (err) => {
160
170
  if (timeout) clearTimeout(timeout)
171
+ await unlink(promptFile).catch(() => {})
161
172
  reject(err)
162
173
  })
163
174
  })