@noice-tech/pi-changelog 1.0.0 → 1.0.2

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
@@ -32,6 +32,8 @@ Pi packages run with the permissions granted to Pi. **Only use this package when
32
32
 
33
33
  `auto` is accepted only as `/commit` inference input. Changelog and PR classifications are `feat`, `fix`, `improve`, or `internal`.
34
34
 
35
+ `/commit` runs its worker on a side branch of the current session at low thinking, then restores your previous thinking level when it finishes. If you invoke it during an active agent turn, the change-type selector opens immediately; after your selection, the command waits for that turn to settle before starting the worker.
36
+
35
37
  The canonical shared classification rules live in `extensions/changelog/rules.md`.
36
38
 
37
39
  ## Repository-specific release-note style
@@ -30,7 +30,7 @@ const CHANGE_TYPE_OPTIONS: Array<{ type: ChangeType; label: string }> = [
30
30
 
31
31
  const MESSAGE_TYPE = 'noice-changelog-commit-result'
32
32
  const PROMPT_MESSAGE_TYPE = 'noice-changelog-commit-worker-prompt'
33
- const STATUS_KEY = 'noice-changelog'
33
+ const COMMIT_WORKER_WIDGET_KEY = 'noice-changelog-commit-worker'
34
34
 
35
35
  type CommitDisplayStatus = 'ok' | 'cancelled' | 'failed'
36
36
 
@@ -41,6 +41,7 @@ interface CommitResultDetails {
41
41
  status?: CommitDisplayStatus
42
42
  }
43
43
 
44
+ let commitCommandPending = false
44
45
  let commitWorkerRunning = false
45
46
  let agentEndWaiter: ((messages: unknown[]) => void) | undefined
46
47
  let latestCommitWorkerMessages: unknown[] | undefined
@@ -154,26 +155,40 @@ export default function noiceChangelogExtension(pi: ExtensionAPI) {
154
155
  'Commit changes and create/update PR. Usage: /commit <changeType> <what was done>',
155
156
  getArgumentCompletions: getCommitArgumentCompletions,
156
157
  handler: async (args, ctx) => {
157
- if (commitWorkerRunning) {
158
- ctx.ui.notify('Commit worker is already running', 'warning')
158
+ if (commitCommandPending || commitWorkerRunning) {
159
+ ctx.ui.notify('Commit command is already active', 'warning')
159
160
  return
160
161
  }
161
162
 
162
- await ctx.waitForIdle()
163
+ commitCommandPending = true
164
+ let prepared: Awaited<ReturnType<typeof prepareCommit>>
165
+ try {
166
+ prepared = await prepareCommit(args, ctx)
167
+ } catch (error) {
168
+ commitCommandPending = false
169
+ throw error
170
+ }
163
171
 
164
- const parsed = await resolveChangeTypeAndContext(args, ctx)
165
- if (!parsed) {
172
+ if (!prepared) {
173
+ commitCommandPending = false
166
174
  return
167
175
  }
168
176
 
177
+ const { parsed, prompt } = prepared
169
178
  const startLeafId = ctx.sessionManager.getLeafId()
170
- const prompt = await buildWorkerPrompt(parsed.changeType, parsed.context)
179
+ const previousThinkingLevel = pi.getThinkingLevel()
171
180
 
181
+ // Establish the running guard before releasing the pending guard. Keeping
182
+ // this transition synchronous prevents a re-entrant command from starting
183
+ // a second worker and overwriting the singleton agent-end waiter.
172
184
  commitWorkerRunning = true
173
- ctx.ui.setStatus(STATUS_KEY, 'running in session branch...')
174
- ctx.ui.notify(`Starting commit worker (${parsed.changeType})`, 'info')
185
+ commitCommandPending = false
175
186
 
176
187
  try {
188
+ showCommitWorkerBanner(ctx)
189
+ ctx.ui.notify(`Starting commit worker (${parsed.changeType})`, 'info')
190
+ pi.setThinkingLevel('low')
191
+
177
192
  const agentEnd = waitForNextAgentEndAfterIdle(ctx)
178
193
  latestCommitWorkerMessages = undefined
179
194
  pi.sendMessage(
@@ -302,7 +317,8 @@ export default function noiceChangelogExtension(pi: ExtensionAPI) {
302
317
  })
303
318
  ctx.ui.notify(`Commit worker failed:\n${message}`, 'error')
304
319
  } finally {
305
- ctx.ui.setStatus(STATUS_KEY, undefined)
320
+ pi.setThinkingLevel(previousThinkingLevel)
321
+ ctx.ui.setWidget(COMMIT_WORKER_WIDGET_KEY, undefined)
306
322
  commitWorkerRunning = false
307
323
  latestCommitWorkerMessages = undefined
308
324
  }
@@ -310,6 +326,20 @@ export default function noiceChangelogExtension(pi: ExtensionAPI) {
310
326
  })
311
327
  }
312
328
 
329
+ function showCommitWorkerBanner(ctx: ExtensionCommandContext) {
330
+ const message = 'Commit worker running on a side branch of this session…'
331
+
332
+ if (ctx.mode !== 'tui') {
333
+ ctx.ui.setWidget(COMMIT_WORKER_WIDGET_KEY, [message])
334
+ return
335
+ }
336
+
337
+ ctx.ui.setWidget(
338
+ COMMIT_WORKER_WIDGET_KEY,
339
+ (_tui, theme) => new Text(theme.fg('warning', message), 1, 0)
340
+ )
341
+ }
342
+
313
343
  function getCommitArgumentCompletions(prefix: string) {
314
344
  const trimmedStart = prefix.trimStart()
315
345
  const leadingWhitespace = prefix.slice(0, prefix.length - trimmedStart.length)
@@ -341,6 +371,29 @@ function getCommitArgumentCompletions(prefix: string) {
341
371
  ]
342
372
  }
343
373
 
374
+ async function prepareCommit(
375
+ args: string | undefined,
376
+ ctx: ExtensionCommandContext
377
+ ) {
378
+ const parsed = await resolveChangeTypeAndContext(args, ctx)
379
+ if (!parsed) return null
380
+
381
+ if (!ctx.isIdle()) {
382
+ ctx.ui.notify(
383
+ 'Commit queued; waiting for the current agent turn to finish',
384
+ 'info'
385
+ )
386
+ }
387
+
388
+ await ctx.waitForIdle()
389
+ const prompt = await buildWorkerPrompt(parsed.changeType, parsed.context)
390
+ // Prompt loading is asynchronous. Re-check idle so another user turn cannot
391
+ // slip in between the original wait and worker startup.
392
+ await ctx.waitForIdle()
393
+
394
+ return { parsed, prompt }
395
+ }
396
+
344
397
  async function resolveChangeTypeAndContext(
345
398
  args: string | undefined,
346
399
  ctx: ExtensionCommandContext
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@noice-tech/pi-changelog",
3
- "version": "1.0.0",
3
+ "version": "1.0.2",
4
4
  "description": "Pi changelog workflow for commits, pull requests, and public release notes.",
5
5
  "type": "module",
6
6
  "license": "MIT",
@@ -48,6 +48,6 @@
48
48
  },
49
49
  "scripts": {
50
50
  "typecheck": "tsc --noEmit --allowImportingTsExtensions --moduleResolution bundler --module ESNext --target ES2022 --skipLibCheck extensions/changelog/index.ts",
51
- "test": "node ../../scripts/smoke-pack.mjs @noice-tech/pi-changelog packages/changelog"
51
+ "test": "node --test test/*.test.mjs && node ../../scripts/smoke-pack.mjs @noice-tech/pi-changelog packages/changelog"
52
52
  }
53
53
  }