crewly 1.20.213 → 1.20.215

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.
Files changed (91) hide show
  1. package/config/skills/agent/core/project-tickets/SKILL.md +42 -10
  2. package/config/skills/agent/core/project-tickets/execute.sh +45 -12
  3. package/config/skills/agent/core/project-tickets/execute.test.sh +19 -0
  4. package/dist/backend/backend/src/constants.d.ts +124 -9
  5. package/dist/backend/backend/src/constants.d.ts.map +1 -1
  6. package/dist/backend/backend/src/constants.js +152 -8
  7. package/dist/backend/backend/src/constants.js.map +1 -1
  8. package/dist/backend/backend/src/controllers/project-tickets/project-tickets.controller.d.ts +9 -1
  9. package/dist/backend/backend/src/controllers/project-tickets/project-tickets.controller.d.ts.map +1 -1
  10. package/dist/backend/backend/src/controllers/project-tickets/project-tickets.controller.js +13 -1
  11. package/dist/backend/backend/src/controllers/project-tickets/project-tickets.controller.js.map +1 -1
  12. package/dist/backend/backend/src/controllers/project-tickets/project-tickets.routes.d.ts +2 -1
  13. package/dist/backend/backend/src/controllers/project-tickets/project-tickets.routes.d.ts.map +1 -1
  14. package/dist/backend/backend/src/controllers/project-tickets/project-tickets.routes.js +4 -2
  15. package/dist/backend/backend/src/controllers/project-tickets/project-tickets.routes.js.map +1 -1
  16. package/dist/backend/backend/src/controllers/talk/talk-transcribe.controller.d.ts +37 -0
  17. package/dist/backend/backend/src/controllers/talk/talk-transcribe.controller.d.ts.map +1 -0
  18. package/dist/backend/backend/src/controllers/talk/talk-transcribe.controller.js +97 -0
  19. package/dist/backend/backend/src/controllers/talk/talk-transcribe.controller.js.map +1 -0
  20. package/dist/backend/backend/src/controllers/talk/talk-transcribe.routes.d.ts +18 -0
  21. package/dist/backend/backend/src/controllers/talk/talk-transcribe.routes.d.ts.map +1 -0
  22. package/dist/backend/backend/src/controllers/talk/talk-transcribe.routes.js +25 -0
  23. package/dist/backend/backend/src/controllers/talk/talk-transcribe.routes.js.map +1 -0
  24. package/dist/backend/backend/src/index.d.ts.map +1 -1
  25. package/dist/backend/backend/src/index.js +22 -4
  26. package/dist/backend/backend/src/index.js.map +1 -1
  27. package/dist/backend/backend/src/routes/api.routes.d.ts.map +1 -1
  28. package/dist/backend/backend/src/routes/api.routes.js +4 -0
  29. package/dist/backend/backend/src/routes/api.routes.js.map +1 -1
  30. package/dist/backend/backend/src/services/cloud/mobile-api-relay.service.d.ts.map +1 -1
  31. package/dist/backend/backend/src/services/cloud/mobile-api-relay.service.js +6 -0
  32. package/dist/backend/backend/src/services/cloud/mobile-api-relay.service.js.map +1 -1
  33. package/dist/backend/backend/src/services/project-tickets/autopilot-speed-command.d.ts +108 -0
  34. package/dist/backend/backend/src/services/project-tickets/autopilot-speed-command.d.ts.map +1 -0
  35. package/dist/backend/backend/src/services/project-tickets/autopilot-speed-command.js +223 -0
  36. package/dist/backend/backend/src/services/project-tickets/autopilot-speed-command.js.map +1 -0
  37. package/dist/backend/backend/src/services/project-tickets/autopilot-speed.wiring.d.ts +57 -0
  38. package/dist/backend/backend/src/services/project-tickets/autopilot-speed.wiring.d.ts.map +1 -0
  39. package/dist/backend/backend/src/services/project-tickets/autopilot-speed.wiring.js +90 -0
  40. package/dist/backend/backend/src/services/project-tickets/autopilot-speed.wiring.js.map +1 -0
  41. package/dist/backend/backend/src/services/project-tickets/project-ticket-workflow.service.d.ts +18 -4
  42. package/dist/backend/backend/src/services/project-tickets/project-ticket-workflow.service.d.ts.map +1 -1
  43. package/dist/backend/backend/src/services/project-tickets/project-ticket-workflow.service.js +18 -4
  44. package/dist/backend/backend/src/services/project-tickets/project-ticket-workflow.service.js.map +1 -1
  45. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot-decision.d.ts +135 -14
  46. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot-decision.d.ts.map +1 -1
  47. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot-decision.js +111 -18
  48. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot-decision.js.map +1 -1
  49. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot-messages.d.ts +67 -1
  50. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot-messages.d.ts.map +1 -1
  51. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot-messages.js +75 -1
  52. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot-messages.js.map +1 -1
  53. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot-trace.d.ts +1 -1
  54. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot-trace.d.ts.map +1 -1
  55. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot-trace.js +7 -0
  56. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot-trace.js.map +1 -1
  57. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot.service.d.ts +99 -4
  58. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot.service.d.ts.map +1 -1
  59. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot.service.js +422 -11
  60. package/dist/backend/backend/src/services/project-tickets/ticket-autopilot.service.js.map +1 -1
  61. package/dist/backend/backend/src/services/slack/slack-initializer.d.ts.map +1 -1
  62. package/dist/backend/backend/src/services/slack/slack-initializer.js +2 -1
  63. package/dist/backend/backend/src/services/slack/slack-initializer.js.map +1 -1
  64. package/dist/backend/backend/src/services/talk/talk-transcribe.service.d.ts +344 -0
  65. package/dist/backend/backend/src/services/talk/talk-transcribe.service.d.ts.map +1 -0
  66. package/dist/backend/backend/src/services/talk/talk-transcribe.service.js +642 -0
  67. package/dist/backend/backend/src/services/talk/talk-transcribe.service.js.map +1 -0
  68. package/dist/backend/backend/src/types/ticket-autopilot.types.d.ts +46 -4
  69. package/dist/backend/backend/src/types/ticket-autopilot.types.d.ts.map +1 -1
  70. package/dist/backend/backend/src/types/ticket-autopilot.types.js +43 -2
  71. package/dist/backend/backend/src/types/ticket-autopilot.types.js.map +1 -1
  72. package/dist/backend/backend/src/types/v2/work-item.types.d.ts +1 -1
  73. package/dist/backend/backend/src/types/v2/work-item.types.d.ts.map +1 -1
  74. package/dist/backend/backend/src/types/v2/work-item.types.js +1 -0
  75. package/dist/backend/backend/src/types/v2/work-item.types.js.map +1 -1
  76. package/dist/backend/build-info.json +2 -2
  77. package/dist/cli/backend/src/constants.d.ts +124 -9
  78. package/dist/cli/backend/src/constants.d.ts.map +1 -1
  79. package/dist/cli/backend/src/constants.js +152 -8
  80. package/dist/cli/backend/src/constants.js.map +1 -1
  81. package/dist/cli/backend/src/types/ticket-autopilot.types.d.ts +46 -4
  82. package/dist/cli/backend/src/types/ticket-autopilot.types.d.ts.map +1 -1
  83. package/dist/cli/backend/src/types/ticket-autopilot.types.js +43 -2
  84. package/dist/cli/backend/src/types/ticket-autopilot.types.js.map +1 -1
  85. package/dist/cli/backend/src/types/v2/work-item.types.d.ts +1 -1
  86. package/dist/cli/backend/src/types/v2/work-item.types.d.ts.map +1 -1
  87. package/dist/cli/backend/src/types/v2/work-item.types.js +1 -0
  88. package/dist/cli/backend/src/types/v2/work-item.types.js.map +1 -1
  89. package/frontend/dist/assets/{index-917db1b8.js → index-839f4374.js} +272 -272
  90. package/frontend/dist/index.html +1 -1
  91. package/package.json +1 -1
@@ -123,9 +123,11 @@ export const TICKET_AUTOPILOT_CONSTANTS = {
123
123
  /** WorkItem type / `metadata.kind` of the goal replan the driver receives when nothing is left to triage */
124
124
  REPLAN_WORK_ITEM_TYPE: 'goal_replan',
125
125
  REPLAN_METADATA_KIND: 'goal_replan',
126
- /** Default and largest number of goal replans per project per local day (0 = off) */
127
- DEFAULT_REPLANS_PER_DAY: 1,
128
- REPLANS_PER_DAY_LIMIT: 5,
126
+ /**
127
+ * Largest explicit `replansPerDay` (0 = off). Absent, the speed mode's
128
+ * daily cap applies ({@link TICKET_AUTOPILOT_CONSTANTS.SPEED_MODES}).
129
+ */
130
+ REPLANS_PER_DAY_LIMIT: 12,
129
131
  /** Tickets closed (done / cancelled) this many days back are listed in the replan brief */
130
132
  REPLAN_CLOSED_LOOKBACK_DAYS: 7,
131
133
  /** Most closed tickets listed in the replan brief */
@@ -145,14 +147,79 @@ export const TICKET_AUTOPILOT_CONSTANTS = {
145
147
  REPLAN_TTL_HOURS_LIMIT: 48,
146
148
  /** A live replan older than this stops holding triage once there are tickets to triage (ms) */
147
149
  REPLAN_YIELD_AFTER_MS: 60 * 60 * 1000,
148
- /**
149
- * After a replan that opened no tickets: skip the next 2 days, then 4,
150
- * then 7 (doubling, capped). Reset by a new goal / OKR or a new ticket.
150
+ /*
151
+ * After a replan that opened no tickets the next one waits for the speed
152
+ * mode's `emptyReplanRetry` (1 h / next day / next week). Reset by a new
153
+ * goal / OKR or a new ticket.
151
154
  */
152
- REPLAN_BACKOFF_FIRST_DAYS: 2,
153
- REPLAN_BACKOFF_MAX_DAYS: 7,
154
155
  /** Goals-log entries older than this are not an active goal (days); OKRs keep their own status */
155
156
  REPLAN_GOAL_ACTIVE_DAYS: 30,
157
+ // --- Speed modes (specs/2026-10-04-autopilot-speed-modes.md) ---
158
+ /** Speed modes, slowest last */
159
+ SPEED_MODE_NAMES: ['rush', 'normal', 'chill'],
160
+ /** Mode of a project that never set one (every project before speed modes) */
161
+ DEFAULT_SPEED_MODE: 'normal',
162
+ /**
163
+ * What each mode supplies. Explicit settings win: `dailyBudgetTokens`
164
+ * (and boosts) over the mode's budget, `replansPerDay` over its daily cap.
165
+ *
166
+ * - `replanMinGapMs` — a replan never starts sooner than this after the last one
167
+ * - `replansPerDayCap` — hard cap per local day (the safety brake)
168
+ * - `selfReviewEveryMs` — cadence of the driver's self-review
169
+ * - `emptyReplanRetry` — after a replan that opened no tickets: retry this
170
+ * many hours later, or on the local day this many days after the replan's day
171
+ * - `dailyBudgetTokens` — the budget when the project sets none
172
+ */
173
+ SPEED_MODES: {
174
+ rush: {
175
+ replanMinGapMs: 60 * 60 * 1000,
176
+ replansPerDayCap: 12,
177
+ selfReviewEveryMs: 60 * 60 * 1000,
178
+ emptyReplanRetry: { unit: 'hours', amount: 1 },
179
+ dailyBudgetTokens: 50_000_000,
180
+ },
181
+ normal: {
182
+ replanMinGapMs: 3 * 60 * 60 * 1000,
183
+ replansPerDayCap: 4,
184
+ selfReviewEveryMs: 24 * 60 * 60 * 1000,
185
+ emptyReplanRetry: { unit: 'days', amount: 1 },
186
+ dailyBudgetTokens: 20_000_000,
187
+ },
188
+ chill: {
189
+ replanMinGapMs: 0,
190
+ replansPerDayCap: 1,
191
+ selfReviewEveryMs: 7 * 24 * 60 * 60 * 1000,
192
+ emptyReplanRetry: { unit: 'days', amount: 7 },
193
+ dailyBudgetTokens: 8_000_000,
194
+ },
195
+ },
196
+ /** WorkItem type / `metadata.kind` of the driver's self-review */
197
+ SELF_REVIEW_WORK_ITEM_TYPE: 'autopilot_self_review',
198
+ SELF_REVIEW_METADATA_KIND: 'autopilot_self_review',
199
+ /** A self-review still live after this long no longer holds the next one (a queued one is cancelled) */
200
+ SELF_REVIEW_LIVE_MAX_MS: 2 * 60 * 60 * 1000,
201
+ /** Longest self-review field accepted (chars) */
202
+ SELF_REVIEW_FIELD_MAX_CHARS: 600,
203
+ /** Self-reviews kept per project (newest last) */
204
+ SELF_REVIEW_HISTORY: 10,
205
+ /** Most characters of the goal quoted in the self-review brief */
206
+ SELF_REVIEW_GOAL_MAX_CHARS: 800,
207
+ /** A self-review older than this is not shown in the evening digest */
208
+ SELF_REVIEW_DIGEST_MAX_AGE_MS: 24 * 60 * 60 * 1000,
209
+ /** Stop reasons (why the autopilot is not producing work), most decisive first */
210
+ STOP_REASONS: ['paused', 'budget_reached', 'system_error', 'waiting_on_owner', 'no_ideas'],
211
+ /** Failed project WorkItems this recent count as a system error (ms) */
212
+ STOP_SYSTEM_ERROR_LOOKBACK_MS: 6 * 60 * 60 * 1000,
213
+ /** An autopilot WorkItem still queued this long is stuck delivery (a system error, ms) */
214
+ STOP_STUCK_DELIVERY_MS: 60 * 60 * 1000,
215
+ /** The metric line of a replan ticket (`Metric: <goal metric> → <expected effect>`) */
216
+ METRIC_LINE_PREFIX: 'Metric: ',
217
+ /** Shortest metric reference accepted (chars) */
218
+ METRIC_MIN_CHARS: 5,
219
+ /** Longest metric reference accepted (chars) */
220
+ METRIC_MAX_CHARS: 300,
221
+ /** How often the owner's speed DM command re-reads the project names (ms) */
222
+ SPEED_PROJECT_CACHE_REFRESH_MS: 60 * 1000,
156
223
  };
157
224
  /**
158
225
  * Safe restart: drain in-flight agent turns before a shutdown kills the PTYs,
@@ -5590,6 +5657,83 @@ export const CLOUD_TALK_CONSTANTS = {
5590
5657
  /** Ticket-intake origin for a Talk message (the portal). */
5591
5658
  INTAKE_ORIGIN: 'portal',
5592
5659
  };
5660
+ /**
5661
+ * Talk voice transcription (specs/2026-10-04-talk-whisper-transcribe.md, #1074):
5662
+ * the portal Talk page records a short clip, sends it over the relay to the
5663
+ * machine of the agent being talked to, and this machine transcribes it with
5664
+ * whisper.cpp — the same engine, binary and model the `transcribe-audio` skill
5665
+ * uses. Nothing is sent to the agent here: the text goes back to the phone for
5666
+ * the owner to check.
5667
+ */
5668
+ export const TALK_TRANSCRIBE_CONSTANTS = {
5669
+ /** Skill whose setup block installs ffmpeg + whisper-cli + the model. */
5670
+ SKILL_ID: 'transcribe-audio',
5671
+ /** Capability advertised to Cloud (heartbeat) while whisper is ready. */
5672
+ CAPABILITY: 'talk_whisper',
5673
+ /** Model file (large-v3-turbo q5_0), same as the skill. */
5674
+ MODEL_FILENAME: 'ggml-large-v3-turbo-q5_0.bin',
5675
+ /** Model directories, in the skill's lookup order (after FLOPOST_WHISPER_MODEL). Relative to the home dir. */
5676
+ MODEL_DIRS: ['.flopost/whisper', '.cache/whisper-models'],
5677
+ /** whisper-cli locations before PATH, in the skill's order (after FLOPOST_WHISPER_BIN). Relative to the home dir. */
5678
+ HOME_BIN_CANDIDATES: ['.flopost/whisper/whisper-cli'],
5679
+ /** whisper.cpp CLI binary name. */
5680
+ WHISPER_BINARY: 'whisper-cli',
5681
+ /** ffmpeg binary name. */
5682
+ FFMPEG_BINARY: 'ffmpeg',
5683
+ /**
5684
+ * Largest clip accepted, in bytes of encoded audio. The relay refuses a
5685
+ * send body over 1 MiB and the clip travels base64 (4/3) inside it, so
5686
+ * 640 KiB of audio leaves room for the envelope.
5687
+ */
5688
+ MAX_AUDIO_BYTES: 640 * 1024,
5689
+ /** Longest clip accepted (s). The phone stops recording here too. */
5690
+ MAX_DURATION_SEC: 90,
5691
+ /** Whole request deadline, including the wait for the one-at-a-time slot (ms). */
5692
+ REQUEST_TIMEOUT_MS: 45_000,
5693
+ /** Requests allowed to wait behind the running one; more are refused as `busy`. */
5694
+ MAX_QUEUE: 3,
5695
+ /** Sample rate whisper.cpp wants. */
5696
+ SAMPLE_RATE: 16_000,
5697
+ /** Bytes per second of 16 kHz mono 16-bit PCM (for the duration of the WAV). */
5698
+ WAV_BYTES_PER_SEC: 32_000,
5699
+ /** WAV header size (bytes) left off when measuring the duration. */
5700
+ WAV_HEADER_BYTES: 44,
5701
+ /** Threads for whisper-cli: CPU count minus this, never below MIN_THREADS. */
5702
+ THREADS_RESERVED: 2,
5703
+ MIN_THREADS: 4,
5704
+ /** First sentence of the initial prompt: biases whisper to Simplified Chinese punctuation and script. */
5705
+ PROMPT_PREFIX: '以下是普通话的句子。',
5706
+ /** Owner glossary always in the vocabulary prompt. */
5707
+ GLOSSARY: ['Crewly', 'CE', 'Crewly Cloud', 'Slack'],
5708
+ /** Upper bound on the vocabulary part of the prompt (characters); whisper keeps ~224 prompt tokens. */
5709
+ MAX_VOCAB_CHARS: 400,
5710
+ /** Language hints the caller may pass (`auto` = whisper detects; zh/en mixed works). */
5711
+ LANGUAGES: ['auto', 'zh', 'en'],
5712
+ /** Audio container types accepted, mapped to the temp file extension ffmpeg sees. */
5713
+ MIME_EXTENSIONS: {
5714
+ 'audio/mp4': 'm4a',
5715
+ 'audio/aac': 'aac',
5716
+ 'audio/x-m4a': 'm4a',
5717
+ 'audio/m4a': 'm4a',
5718
+ 'audio/webm': 'webm',
5719
+ 'audio/ogg': 'ogg',
5720
+ 'audio/wav': 'wav',
5721
+ 'audio/x-wav': 'wav',
5722
+ 'audio/mpeg': 'mp3',
5723
+ },
5724
+ /** Temp dir prefix (under the OS temp dir); removed after every request. */
5725
+ TEMP_PREFIX: 'crewly-talk-stt-',
5726
+ /** Error codes the phone reacts to (any of them = fall back to on-device recognition). */
5727
+ CODES: {
5728
+ WHISPER_UNAVAILABLE: 'whisper_unavailable',
5729
+ TOO_LONG: 'too_long',
5730
+ TIMEOUT: 'timeout',
5731
+ FAILED: 'failed',
5732
+ BUSY: 'busy',
5733
+ INVALID_AUDIO: 'invalid_audio',
5734
+ OWNER_ONLY: 'owner_only',
5735
+ },
5736
+ };
5593
5737
  /**
5594
5738
  * "Waiting on you" synced to Crewly Cloud (specs/unified-conversations-cloud-store.md §F, Phase 5):
5595
5739
  * tickets in 待验收 are uploaded as text snapshots; the owner's accept /