@miller-tech/uap 2.16.6 → 2.19.5

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 (105) hide show
  1. package/README.md +1 -1
  2. package/config/capacity-policy.json +33 -0
  3. package/config/model-profiles/qwen38.json +32 -33
  4. package/dist/.tsbuildinfo +1 -1
  5. package/dist/bin/cli.js +57 -0
  6. package/dist/bin/cli.js.map +1 -1
  7. package/dist/capacity/policy.d.ts +32 -1
  8. package/dist/capacity/policy.d.ts.map +1 -1
  9. package/dist/capacity/policy.js +123 -4
  10. package/dist/capacity/policy.js.map +1 -1
  11. package/dist/capacity/probe.d.ts +26 -0
  12. package/dist/capacity/probe.d.ts.map +1 -1
  13. package/dist/capacity/probe.js +84 -3
  14. package/dist/capacity/probe.js.map +1 -1
  15. package/dist/cli/inference.d.ts +4 -0
  16. package/dist/cli/inference.d.ts.map +1 -1
  17. package/dist/cli/inference.js +74 -8
  18. package/dist/cli/inference.js.map +1 -1
  19. package/dist/cli/merge-gate.d.ts +59 -0
  20. package/dist/cli/merge-gate.d.ts.map +1 -0
  21. package/dist/cli/merge-gate.js +238 -0
  22. package/dist/cli/merge-gate.js.map +1 -0
  23. package/dist/cli/merge-queue.d.ts +13 -0
  24. package/dist/cli/merge-queue.d.ts.map +1 -1
  25. package/dist/cli/merge-queue.js +48 -2
  26. package/dist/cli/merge-queue.js.map +1 -1
  27. package/dist/cli/mission.d.ts +25 -0
  28. package/dist/cli/mission.d.ts.map +1 -0
  29. package/dist/cli/mission.js +225 -0
  30. package/dist/cli/mission.js.map +1 -0
  31. package/dist/cli/orch.d.ts +27 -0
  32. package/dist/cli/orch.d.ts.map +1 -0
  33. package/dist/cli/orch.js +70 -0
  34. package/dist/cli/orch.js.map +1 -0
  35. package/dist/cli/systemd-services.d.ts.map +1 -1
  36. package/dist/cli/systemd-services.js +44 -0
  37. package/dist/cli/systemd-services.js.map +1 -1
  38. package/dist/delivery/merge-gate.d.ts +168 -0
  39. package/dist/delivery/merge-gate.d.ts.map +1 -0
  40. package/dist/delivery/merge-gate.js +309 -0
  41. package/dist/delivery/merge-gate.js.map +1 -0
  42. package/dist/inference/analysis.d.ts +69 -3
  43. package/dist/inference/analysis.d.ts.map +1 -1
  44. package/dist/inference/analysis.js +123 -7
  45. package/dist/inference/analysis.js.map +1 -1
  46. package/dist/inference/probe.d.ts +38 -1
  47. package/dist/inference/probe.d.ts.map +1 -1
  48. package/dist/inference/probe.js +303 -30
  49. package/dist/inference/probe.js.map +1 -1
  50. package/dist/inference/strata.d.ts +95 -0
  51. package/dist/inference/strata.d.ts.map +1 -0
  52. package/dist/inference/strata.js +167 -0
  53. package/dist/inference/strata.js.map +1 -0
  54. package/dist/mission/database.d.ts +29 -0
  55. package/dist/mission/database.d.ts.map +1 -0
  56. package/dist/mission/database.js +131 -0
  57. package/dist/mission/database.js.map +1 -0
  58. package/dist/mission/ledger.d.ts +109 -0
  59. package/dist/mission/ledger.d.ts.map +1 -0
  60. package/dist/mission/ledger.js +294 -0
  61. package/dist/mission/ledger.js.map +1 -0
  62. package/dist/mission/poll-cycle.d.ts +73 -0
  63. package/dist/mission/poll-cycle.d.ts.map +1 -0
  64. package/dist/mission/poll-cycle.js +100 -0
  65. package/dist/mission/poll-cycle.js.map +1 -0
  66. package/dist/mission/poll-executor.d.ts +91 -0
  67. package/dist/mission/poll-executor.d.ts.map +1 -0
  68. package/dist/mission/poll-executor.js +328 -0
  69. package/dist/mission/poll-executor.js.map +1 -0
  70. package/dist/models/types.d.ts.map +1 -1
  71. package/dist/models/types.js +33 -27
  72. package/dist/models/types.js.map +1 -1
  73. package/dist/self-tuning/profiles/qwen38.d.ts +13 -14
  74. package/dist/self-tuning/profiles/qwen38.d.ts.map +1 -1
  75. package/dist/self-tuning/profiles/qwen38.js +17 -18
  76. package/dist/self-tuning/profiles/qwen38.js.map +1 -1
  77. package/dist/types/mission.d.ts +80 -0
  78. package/dist/types/mission.d.ts.map +1 -0
  79. package/dist/types/mission.js +12 -0
  80. package/dist/types/mission.js.map +1 -0
  81. package/docs/architecture/adr/0003-mission-orchestrator.md +99 -0
  82. package/docs/architecture/adr/0004-deterministic-merge-gate.md +127 -0
  83. package/docs/guides/CAPACITY_POLICY.md +49 -0
  84. package/docs/guides/INFERENCE_HEALTH.md +65 -8
  85. package/docs/guides/MISSIONS.md +170 -0
  86. package/docs/guides/PROXY.md +2 -0
  87. package/docs/reports/2026-10-02-plane-admin-fail-closed.md +70 -0
  88. package/docs/reports/2026-10-02-plane-admin-protect-session.md +116 -0
  89. package/docs/visual/merge-gate.html +404 -0
  90. package/docs/visual/mission-orchestrator.html +472 -0
  91. package/package.json +2 -2
  92. package/src/policies/enforcers/__pycache__/_common.cpython-312.pyc +0 -0
  93. package/src/policies/enforcers/__pycache__/expert_review_required.cpython-312.pyc +0 -0
  94. package/src/policies/enforcers/__pycache__/quality_metrics_gate.cpython-312.pyc +0 -0
  95. package/src/policies/enforcers/plane_admin_protect.py +133 -0
  96. package/src/policies/schemas/policies/plane-admin-protect.md +55 -0
  97. package/templates/hooks/__pycache__/deliver_autoroute.cpython-312.pyc +0 -0
  98. package/templates/hooks/uap-policy-gate.sh +33 -0
  99. package/tools/agents/scripts/__pycache__/toolcall_path_normalizer.cpython-312.pyc +0 -0
  100. package/tools/agents/scripts/anthropic_proxy.py +522 -45
  101. package/tools/agents/tests/test_anthropic_proxy_streaming.py +171 -0
  102. package/tools/agents/tests/test_gate_failclosed_plane_admin.py +248 -0
  103. package/tools/agents/tests/test_plane_admin_protect.py +124 -0
  104. package/tools/agents/tests/test_repeat_call_guard.py +64 -0
  105. package/tools/agents/tests/test_stream_heartbeat.py +77 -0
@@ -107,5 +107,82 @@ class TestStreamHeartbeat(unittest.TestCase):
107
107
  self.assertIn("kaboom", out)
108
108
 
109
109
 
110
+ class TestGuardedWaitProgressLog(unittest.TestCase):
111
+ """Journal progress during the buffered wait (2026-10-04 incident).
112
+
113
+ A no-tool streaming turn served via the guarded path can buffer for
114
+ minutes (live: an 11,099-token client-compaction summary over 281 s) with
115
+ the journal silent from REQ to RESP — the proxy read as hung and the only
116
+ evidence was the RESP timestamp. `_heartbeat_then_buffered` now logs one
117
+ INFO line per PROXY_GUARDED_WAIT_LOG_SECS of waiting so a long buffered
118
+ generation is legible while it happens.
119
+ """
120
+
121
+ def setUp(self):
122
+ self._hb = proxy.PROXY_STREAM_HEARTBEAT_SECS
123
+ self._log_secs = proxy.PROXY_GUARDED_WAIT_LOG_SECS
124
+ proxy.PROXY_STREAM_HEARTBEAT_SECS = 0.05
125
+ proxy.PROXY_GUARDED_WAIT_LOG_SECS = 0.06
126
+
127
+ def tearDown(self):
128
+ proxy.PROXY_STREAM_HEARTBEAT_SECS = self._hb
129
+ proxy.PROXY_GUARDED_WAIT_LOG_SECS = self._log_secs
130
+
131
+ @staticmethod
132
+ def _response():
133
+ return {
134
+ "id": "msg_z",
135
+ "model": "m",
136
+ "content": [{"type": "text", "text": "done"}],
137
+ "stop_reason": "end_turn",
138
+ "usage": {"output_tokens": 1},
139
+ }
140
+
141
+ def test_slow_produce_logs_wait_progress(self):
142
+ async def produce():
143
+ await asyncio.sleep(0.2) # > 2 log boundaries at 0.06s
144
+ return self._response()
145
+
146
+ with self.assertLogs("uap.anthropic_proxy", level="INFO") as cm:
147
+ out = "".join(asyncio.run(_collect(produce())))
148
+ self.assertIn("done", out) # stream still completes normally
149
+ wait_logs = [l for l in cm.output if "GUARDED-BUFFER WAIT" in l]
150
+ self.assertGreaterEqual(len(wait_logs), 2)
151
+ self.assertIn("still generating after", wait_logs[0])
152
+ self.assertIn("test-model", wait_logs[0])
153
+
154
+ def test_progress_logs_once_per_boundary_not_per_heartbeat(self):
155
+ async def produce():
156
+ await asyncio.sleep(0.22) # ~4 heartbeats, ~3 boundaries
157
+ return self._response()
158
+
159
+ with self.assertLogs("uap.anthropic_proxy", level="INFO") as cm:
160
+ asyncio.run(_collect(produce()))
161
+ wait_logs = [l for l in cm.output if "GUARDED-BUFFER WAIT" in l]
162
+ # 0.22s of waiting at 0.06s boundaries: 2-4 lines, one per boundary
163
+ # crossed — NOT one per 0.05s heartbeat.
164
+ self.assertGreaterEqual(len(wait_logs), 2)
165
+ self.assertLessEqual(len(wait_logs), 4)
166
+
167
+ def test_fast_produce_logs_no_wait_progress(self):
168
+ async def produce():
169
+ return self._response()
170
+
171
+ with self.assertNoLogs("uap.anthropic_proxy", level="INFO"):
172
+ out = "".join(asyncio.run(_collect(produce())))
173
+ self.assertIn("done", out)
174
+
175
+ def test_wait_progress_log_disabled(self):
176
+ proxy.PROXY_GUARDED_WAIT_LOG_SECS = 0.0
177
+
178
+ async def produce():
179
+ await asyncio.sleep(0.15)
180
+ return self._response()
181
+
182
+ with self.assertNoLogs("uap.anthropic_proxy", level="INFO"):
183
+ out = "".join(asyncio.run(_collect(produce())))
184
+ self.assertIn("done", out)
185
+
186
+
110
187
  if __name__ == "__main__":
111
188
  unittest.main()