@webex/contact-center 3.11.0 → 3.12.0-auth-prejoin-fetch.1

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 (325) hide show
  1. package/.sdd/manifest.json +883 -0
  2. package/AGENTS.md +94 -0
  3. package/ai-docs/ARCHITECTURE.md +168 -0
  4. package/ai-docs/CONTRACTS.md +50 -0
  5. package/ai-docs/GETTING_STARTED.md +168 -0
  6. package/ai-docs/GLOSSARY.md +43 -0
  7. package/ai-docs/README.md +138 -0
  8. package/ai-docs/REVIEW_CHECKLIST.md +41 -0
  9. package/ai-docs/RULES.md +444 -0
  10. package/ai-docs/SECURITY.md +52 -0
  11. package/ai-docs/SERVICE_STATE.md +48 -0
  12. package/ai-docs/SPEC_INDEX.md +65 -0
  13. package/ai-docs/adr/0001-spec-source-policy.md +55 -0
  14. package/ai-docs/adr/README.md +8 -0
  15. package/ai-docs/adr/_adr-template.md +31 -0
  16. package/ai-docs/contact-center-spec.md +359 -0
  17. package/ai-docs/features/consult-transfer-list-policy/spec/feature-spec.md +362 -0
  18. package/ai-docs/features/generated-spec-conformance-fidelity-remediation/spec/feature-spec.md +117 -0
  19. package/ai-docs/features/residual-warning-coverage-completion/spec/feature-spec.md +203 -0
  20. package/ai-docs/features/validator-code-fidelity-drift-fix/spec/feature-spec.md +315 -0
  21. package/ai-docs/patterns/event-driven-patterns.md +485 -0
  22. package/ai-docs/patterns/testing-patterns.md +480 -0
  23. package/ai-docs/patterns/typescript-patterns.md +365 -0
  24. package/ai-docs/templates/README.md +102 -0
  25. package/ai-docs/templates/documentation/create-agents-md.md +240 -0
  26. package/ai-docs/templates/documentation/create-architecture-md.md +295 -0
  27. package/ai-docs/templates/existing-service/bug-fix.md +254 -0
  28. package/ai-docs/templates/existing-service/feature-enhancement.md +450 -0
  29. package/ai-docs/templates/new-method/00-master.md +80 -0
  30. package/ai-docs/templates/new-method/01-requirements.md +232 -0
  31. package/ai-docs/templates/new-method/02-implementation.md +295 -0
  32. package/ai-docs/templates/new-method/03-tests.md +201 -0
  33. package/ai-docs/templates/new-method/04-validation.md +141 -0
  34. package/ai-docs/templates/new-service/00-master.md +109 -0
  35. package/ai-docs/templates/new-service/01-pre-questions.md +159 -0
  36. package/ai-docs/templates/new-service/02-code-generation.md +346 -0
  37. package/ai-docs/templates/new-service/03-integration.md +178 -0
  38. package/ai-docs/templates/new-service/04-test-generation.md +205 -0
  39. package/ai-docs/templates/new-service/05-validation.md +145 -0
  40. package/dist/cc.js +818 -59
  41. package/dist/cc.js.map +1 -1
  42. package/dist/config.js +13 -0
  43. package/dist/config.js.map +1 -1
  44. package/dist/constants.js +31 -3
  45. package/dist/constants.js.map +1 -1
  46. package/dist/index.js +27 -5
  47. package/dist/index.js.map +1 -1
  48. package/dist/metrics/behavioral-events.js +127 -0
  49. package/dist/metrics/behavioral-events.js.map +1 -1
  50. package/dist/metrics/constants.js +34 -3
  51. package/dist/metrics/constants.js.map +1 -1
  52. package/dist/services/AddressBook.js +18 -15
  53. package/dist/services/AddressBook.js.map +1 -1
  54. package/dist/services/AnswerCallOnWebexService.js +174 -0
  55. package/dist/services/AnswerCallOnWebexService.js.map +1 -0
  56. package/dist/services/ApiAiAssistant.js +318 -0
  57. package/dist/services/ApiAiAssistant.js.map +1 -0
  58. package/dist/services/EntryPoint.js +46 -68
  59. package/dist/services/EntryPoint.js.map +1 -1
  60. package/dist/services/Queue.js +27 -22
  61. package/dist/services/Queue.js.map +1 -1
  62. package/dist/services/UserPreference.js +427 -0
  63. package/dist/services/UserPreference.js.map +1 -0
  64. package/dist/services/WebexCrossClientService.js +171 -0
  65. package/dist/services/WebexCrossClientService.js.map +1 -0
  66. package/dist/services/WxAppTelephonyMercurySync.js +93 -0
  67. package/dist/services/WxAppTelephonyMercurySync.js.map +1 -0
  68. package/dist/services/agent/types.js.map +1 -1
  69. package/dist/services/config/Util.js +11 -4
  70. package/dist/services/config/Util.js.map +1 -1
  71. package/dist/services/config/constants.js +45 -8
  72. package/dist/services/config/constants.js.map +1 -1
  73. package/dist/services/config/index.js +41 -2
  74. package/dist/services/config/index.js.map +1 -1
  75. package/dist/services/config/types.js +70 -8
  76. package/dist/services/config/types.js.map +1 -1
  77. package/dist/services/constants.js +27 -1
  78. package/dist/services/constants.js.map +1 -1
  79. package/dist/services/core/Err.js.map +1 -1
  80. package/dist/services/core/Utils.js +122 -25
  81. package/dist/services/core/Utils.js.map +1 -1
  82. package/dist/services/core/WebexRequest.js +6 -2
  83. package/dist/services/core/WebexRequest.js.map +1 -1
  84. package/dist/services/core/aqm-reqs.js +119 -30
  85. package/dist/services/core/aqm-reqs.js.map +1 -1
  86. package/dist/services/core/types.js.map +1 -1
  87. package/dist/services/core/websocket/WebSocketManager.js +22 -6
  88. package/dist/services/core/websocket/WebSocketManager.js.map +1 -1
  89. package/dist/services/core/websocket/connection-service.js +3 -1
  90. package/dist/services/core/websocket/connection-service.js.map +1 -1
  91. package/dist/services/core/websocket/types.js.map +1 -1
  92. package/dist/services/index.js +6 -0
  93. package/dist/services/index.js.map +1 -1
  94. package/dist/services/task/Task.js +754 -0
  95. package/dist/services/task/Task.js.map +1 -0
  96. package/dist/services/task/TaskFactory.js +49 -0
  97. package/dist/services/task/TaskFactory.js.map +1 -0
  98. package/dist/services/task/TaskManager.js +1073 -447
  99. package/dist/services/task/TaskManager.js.map +1 -1
  100. package/dist/services/task/TaskUtils.js +220 -23
  101. package/dist/services/task/TaskUtils.js.map +1 -1
  102. package/dist/services/task/WebexCallingUtils.js +70 -0
  103. package/dist/services/task/WebexCallingUtils.js.map +1 -0
  104. package/dist/services/task/constants.js +26 -2
  105. package/dist/services/task/constants.js.map +1 -1
  106. package/dist/services/task/contact.js +29 -0
  107. package/dist/services/task/contact.js.map +1 -1
  108. package/dist/services/task/dialer.js +129 -0
  109. package/dist/services/task/dialer.js.map +1 -1
  110. package/dist/services/task/digital/Digital.js +78 -0
  111. package/dist/services/task/digital/Digital.js.map +1 -0
  112. package/dist/services/task/state-machine/TaskStateMachine.js +971 -0
  113. package/dist/services/task/state-machine/TaskStateMachine.js.map +1 -0
  114. package/dist/services/task/state-machine/actions.js +572 -0
  115. package/dist/services/task/state-machine/actions.js.map +1 -0
  116. package/dist/services/task/state-machine/constants.js +161 -0
  117. package/dist/services/task/state-machine/constants.js.map +1 -0
  118. package/dist/services/task/state-machine/guards.js +409 -0
  119. package/dist/services/task/state-machine/guards.js.map +1 -0
  120. package/dist/services/task/state-machine/index.js +53 -0
  121. package/dist/services/task/state-machine/index.js.map +1 -0
  122. package/dist/services/task/state-machine/types.js +54 -0
  123. package/dist/services/task/state-machine/types.js.map +1 -0
  124. package/dist/services/task/state-machine/uiControlsComputer.js +703 -0
  125. package/dist/services/task/state-machine/uiControlsComputer.js.map +1 -0
  126. package/dist/services/task/taskDataNormalizer.js +99 -0
  127. package/dist/services/task/taskDataNormalizer.js.map +1 -0
  128. package/dist/services/task/types.js +243 -5
  129. package/dist/services/task/types.js.map +1 -1
  130. package/dist/services/task/voice/Voice.js +1380 -0
  131. package/dist/services/task/voice/Voice.js.map +1 -0
  132. package/dist/services/task/voice/WebRTC.js +152 -0
  133. package/dist/services/task/voice/WebRTC.js.map +1 -0
  134. package/dist/services/task/voice/wxAppVoiceMethods.js +201 -0
  135. package/dist/services/task/voice/wxAppVoiceMethods.js.map +1 -0
  136. package/dist/services/wxAppTelephonyUtils.js +19 -0
  137. package/dist/services/wxAppTelephonyUtils.js.map +1 -0
  138. package/dist/types/cc.d.ts +967 -0
  139. package/dist/types/config.d.ts +79 -0
  140. package/dist/types/constants.d.ts +74 -0
  141. package/dist/types/index.d.ts +201 -0
  142. package/dist/types/logger-proxy.d.ts +71 -0
  143. package/dist/types/metrics/MetricsManager.d.ts +223 -0
  144. package/dist/types/metrics/behavioral-events.d.ts +29 -0
  145. package/dist/types/metrics/constants.d.ts +183 -0
  146. package/dist/types/services/AddressBook.d.ts +75 -0
  147. package/dist/types/services/AnswerCallOnWebexService.d.ts +37 -0
  148. package/dist/types/services/ApiAiAssistant.d.ts +49 -0
  149. package/dist/types/services/EntryPoint.d.ts +69 -0
  150. package/dist/types/services/Queue.d.ts +78 -0
  151. package/dist/types/services/UserPreference.d.ts +118 -0
  152. package/dist/types/services/WebCallingService.d.ts +1 -0
  153. package/dist/types/services/WebexCrossClientService.d.ts +28 -0
  154. package/dist/types/services/WxAppTelephonyMercurySync.d.ts +28 -0
  155. package/dist/types/services/agent/index.d.ts +46 -0
  156. package/dist/types/services/agent/types.d.ts +413 -0
  157. package/dist/types/services/config/Util.d.ts +20 -0
  158. package/dist/types/services/config/constants.d.ts +273 -0
  159. package/dist/types/services/config/index.d.ts +177 -0
  160. package/dist/types/services/config/types.d.ts +1381 -0
  161. package/dist/types/services/constants.d.ts +110 -0
  162. package/dist/types/services/core/Err.d.ts +127 -0
  163. package/dist/types/services/core/GlobalTypes.d.ts +58 -0
  164. package/dist/types/services/core/Utils.d.ts +121 -0
  165. package/dist/types/services/core/WebexRequest.d.ts +23 -0
  166. package/dist/types/services/core/aqm-reqs.d.ts +65 -0
  167. package/dist/types/services/core/constants.d.ts +99 -0
  168. package/dist/types/services/core/types.d.ts +49 -0
  169. package/dist/types/services/core/websocket/WebSocketManager.d.ts +36 -0
  170. package/dist/types/services/core/websocket/connection-service.d.ts +27 -0
  171. package/dist/types/services/core/websocket/keepalive.worker.d.ts +2 -0
  172. package/dist/types/services/core/websocket/types.d.ts +37 -0
  173. package/dist/types/services/index.d.ts +54 -0
  174. package/dist/types/services/task/AutoWrapup.d.ts +40 -0
  175. package/dist/types/services/task/Task.d.ts +175 -0
  176. package/dist/types/services/task/TaskFactory.d.ts +13 -0
  177. package/dist/types/services/task/TaskManager.d.ts +1 -0
  178. package/dist/types/services/task/TaskUtils.d.ts +138 -0
  179. package/dist/types/services/task/WebexCallingUtils.d.ts +11 -0
  180. package/dist/types/services/task/constants.d.ts +94 -0
  181. package/dist/types/services/task/contact.d.ts +73 -0
  182. package/dist/types/services/task/dialer.d.ts +73 -0
  183. package/dist/types/services/task/digital/Digital.d.ts +22 -0
  184. package/dist/types/services/task/state-machine/TaskStateMachine.d.ts +1398 -0
  185. package/dist/types/services/task/state-machine/actions.d.ts +10 -0
  186. package/dist/types/services/task/state-machine/constants.d.ts +107 -0
  187. package/dist/types/services/task/state-machine/guards.d.ts +103 -0
  188. package/dist/types/services/task/state-machine/index.d.ts +13 -0
  189. package/dist/types/services/task/state-machine/types.d.ts +277 -0
  190. package/dist/types/services/task/state-machine/uiControlsComputer.d.ts +9 -0
  191. package/dist/types/services/task/taskDataNormalizer.d.ts +10 -0
  192. package/dist/types/services/task/types.d.ts +1933 -0
  193. package/dist/types/services/task/voice/Voice.d.ts +223 -0
  194. package/dist/types/services/task/voice/WebRTC.d.ts +53 -0
  195. package/dist/types/services/task/voice/wxAppVoiceMethods.d.ts +52 -0
  196. package/dist/types/services/wxAppTelephonyUtils.d.ts +5 -0
  197. package/dist/types/types.d.ts +784 -0
  198. package/dist/types/utils/PageCache.d.ts +190 -0
  199. package/dist/types/webex-config.d.ts +53 -0
  200. package/dist/types/webex.d.ts +8 -0
  201. package/dist/types.js +137 -3
  202. package/dist/types.js.map +1 -1
  203. package/dist/utils/PageCache.js +19 -5
  204. package/dist/utils/PageCache.js.map +1 -1
  205. package/dist/webex.js +14 -2
  206. package/dist/webex.js.map +1 -1
  207. package/package.json +16 -12
  208. package/src/cc.ts +983 -60
  209. package/src/config.ts +13 -0
  210. package/src/constants.ts +29 -1
  211. package/src/index.ts +26 -5
  212. package/src/metrics/ai-docs/AGENTS.md +350 -0
  213. package/src/metrics/ai-docs/ARCHITECTURE.md +338 -0
  214. package/src/metrics/ai-docs/metrics-spec.md +860 -0
  215. package/src/metrics/behavioral-events.ts +134 -0
  216. package/src/metrics/constants.ts +39 -3
  217. package/src/services/AddressBook.ts +17 -6
  218. package/src/services/AnswerCallOnWebexService.ts +206 -0
  219. package/src/services/ApiAiAssistant.ts +412 -0
  220. package/src/services/EntryPoint.ts +59 -60
  221. package/src/services/Queue.ts +29 -12
  222. package/src/services/UserPreference.ts +509 -0
  223. package/src/services/WebexCrossClientService.ts +212 -0
  224. package/src/services/WxAppTelephonyMercurySync.ts +115 -0
  225. package/src/services/agent/ai-docs/AGENTS.md +240 -0
  226. package/src/services/agent/ai-docs/ARCHITECTURE.md +304 -0
  227. package/src/services/agent/ai-docs/agent-spec.md +504 -0
  228. package/src/services/agent/types.ts +1 -1
  229. package/src/services/ai-docs/AGENTS.md +386 -0
  230. package/src/services/ai-docs/services-spec.md +497 -0
  231. package/src/services/config/Util.ts +13 -2
  232. package/src/services/config/ai-docs/AGENTS.md +255 -0
  233. package/src/services/config/ai-docs/ARCHITECTURE.md +426 -0
  234. package/src/services/config/ai-docs/config-spec.md +675 -0
  235. package/src/services/config/constants.ts +47 -7
  236. package/src/services/config/index.ts +45 -1
  237. package/src/services/config/types.ts +253 -11
  238. package/src/services/constants.ts +29 -0
  239. package/src/services/core/Err.ts +4 -0
  240. package/src/services/core/Utils.ts +143 -30
  241. package/src/services/core/WebexRequest.ts +3 -1
  242. package/src/services/core/ai-docs/AGENTS.md +381 -0
  243. package/src/services/core/ai-docs/ARCHITECTURE.md +698 -0
  244. package/src/services/core/ai-docs/core-spec.md +787 -0
  245. package/src/services/core/aqm-reqs.ts +125 -32
  246. package/src/services/core/types.ts +2 -0
  247. package/src/services/core/websocket/WebSocketManager.ts +23 -6
  248. package/src/services/core/websocket/connection-service.ts +5 -1
  249. package/src/services/core/websocket/types.ts +1 -1
  250. package/src/services/index.ts +4 -0
  251. package/src/services/task/Task.ts +908 -0
  252. package/src/services/task/TaskFactory.ts +60 -0
  253. package/src/services/task/TaskManager.ts +1291 -513
  254. package/src/services/task/TaskUtils.ts +314 -24
  255. package/src/services/task/WebexCallingUtils.ts +136 -0
  256. package/src/services/task/ai-docs/AGENTS.md +457 -0
  257. package/src/services/task/ai-docs/ARCHITECTURE.md +595 -0
  258. package/src/services/task/ai-docs/task-spec.md +1469 -0
  259. package/src/services/task/constants.ts +26 -0
  260. package/src/services/task/contact.ts +30 -0
  261. package/src/services/task/dialer.ts +136 -1
  262. package/src/services/task/digital/Digital.ts +97 -0
  263. package/src/services/task/state-machine/TaskStateMachine.ts +1313 -0
  264. package/src/services/task/state-machine/actions.ts +741 -0
  265. package/src/services/task/state-machine/ai-docs/AGENTS.md +462 -0
  266. package/src/services/task/state-machine/ai-docs/ARCHITECTURE.md +1146 -0
  267. package/src/services/task/state-machine/ai-docs/task-state-machine-spec.md +2209 -0
  268. package/src/services/task/state-machine/constants.ts +172 -0
  269. package/src/services/task/state-machine/guards.ts +498 -0
  270. package/src/services/task/state-machine/index.ts +28 -0
  271. package/src/services/task/state-machine/types.ts +258 -0
  272. package/src/services/task/state-machine/uiControlsComputer.ts +1135 -0
  273. package/src/services/task/taskDataNormalizer.ts +137 -0
  274. package/src/services/task/types.ts +843 -70
  275. package/src/services/task/voice/Voice.ts +1720 -0
  276. package/src/services/task/voice/WebRTC.ts +191 -0
  277. package/src/services/task/voice/wxAppVoiceMethods.ts +307 -0
  278. package/src/services/wxAppTelephonyUtils.ts +14 -0
  279. package/src/types.ts +238 -11
  280. package/src/utils/AGENTS.md +289 -0
  281. package/src/utils/PageCache.ts +38 -5
  282. package/src/utils/ai-docs/utils-spec.md +391 -0
  283. package/src/webex.js +2 -0
  284. package/test/unit/spec/cc.ts +1856 -122
  285. package/test/unit/spec/logger-proxy.ts +70 -0
  286. package/test/unit/spec/metrics/behavioral-events.ts +18 -0
  287. package/test/unit/spec/services/AddressBook.ts +37 -6
  288. package/test/unit/spec/services/AnswerCallOnWebexService.ts +223 -0
  289. package/test/unit/spec/services/ApiAiAssistant.ts +273 -0
  290. package/test/unit/spec/services/EntryPoint.ts +87 -40
  291. package/test/unit/spec/services/Queue.ts +123 -12
  292. package/test/unit/spec/services/UserPreference.ts +401 -0
  293. package/test/unit/spec/services/WebCallingService.ts +7 -1
  294. package/test/unit/spec/services/WebexCrossClientService.ts +261 -0
  295. package/test/unit/spec/services/WxAppTelephonyMercurySync.ts +113 -0
  296. package/test/unit/spec/services/config/Util.ts +85 -0
  297. package/test/unit/spec/services/config/index.ts +85 -29
  298. package/test/unit/spec/services/core/Utils.ts +481 -2
  299. package/test/unit/spec/services/core/WebexRequest.ts +3 -1
  300. package/test/unit/spec/services/core/aqm-reqs.ts +113 -1
  301. package/test/unit/spec/services/core/websocket/WebSocketManager.ts +137 -41
  302. package/test/unit/spec/services/core/websocket/connection-service.ts +3 -1
  303. package/test/unit/spec/services/task/AutoWrapup.ts +63 -0
  304. package/test/unit/spec/services/task/Task.ts +677 -0
  305. package/test/unit/spec/services/task/TaskFactory.ts +99 -0
  306. package/test/unit/spec/services/task/TaskManager.ts +2209 -918
  307. package/test/unit/spec/services/task/TaskUtils.ts +235 -0
  308. package/test/unit/spec/services/task/WebexCallingUtils.ts +153 -0
  309. package/test/unit/spec/services/task/contact.ts +33 -0
  310. package/test/unit/spec/services/task/dialer.ts +372 -96
  311. package/test/unit/spec/services/task/digital/Digital.ts +105 -0
  312. package/test/unit/spec/services/task/state-machine/TaskStateMachine.ts +3433 -0
  313. package/test/unit/spec/services/task/state-machine/guards.ts +839 -0
  314. package/test/unit/spec/services/task/state-machine/types.ts +18 -0
  315. package/test/unit/spec/services/task/state-machine/uiControlsComputer.ts +3101 -0
  316. package/test/unit/spec/services/task/taskTestUtils.ts +87 -0
  317. package/test/unit/spec/services/task/voice/Voice.ts +1523 -0
  318. package/test/unit/spec/services/task/voice/WebRTC.ts +235 -0
  319. package/test/unit/spec/services/task/voice/wxAppVoiceMethods.ts +459 -0
  320. package/umd/contact-center.min.js +2 -2
  321. package/umd/contact-center.min.js.map +1 -1
  322. package/dist/services/task/index.js +0 -1525
  323. package/dist/services/task/index.js.map +0 -1
  324. package/src/services/task/index.ts +0 -1801
  325. package/test/unit/spec/services/task/index.ts +0 -2184
@@ -0,0 +1,362 @@
1
+ ---
2
+ type: Feature Spec
3
+ title: Consult and transfer list policy
4
+ description: Centralize consult and transfer destination eligibility, request shaping, ordering, and cache policy in the Contact Center SDK.
5
+ tags: [feature, specification, contact-center, consult-transfer]
6
+ ---
7
+
8
+ # Consult and transfer list policy
9
+
10
+ This document owns the reusable consult/transfer destination-list policy. The SDK applies default telephony eligibility, ordering, profile views, and cache safety through the existing list methods; consumers use compatible existing parameters only when they need a different filter or sort.
11
+
12
+ Related context: [package architecture](../../../ARCHITECTURE.md) · [specification index](../../../SPEC_INDEX.md) · [package instructions](../../../../AGENTS.md)
13
+
14
+ ## Metadata
15
+
16
+ | Field | Value |
17
+ | --- | --- |
18
+ | Feature key | `CAI-8354` |
19
+ | Owner | Webex Contact Center SDK maintainers |
20
+ | Status | Approved and implemented; diff-scoped drift validation PASS; independent validation pending |
21
+ | Work type | Defect |
22
+ | Change class | Contract |
23
+ | Source/intake | Developer-approved consult/transfer behavior review and current code/tests |
24
+ | Last verified | 2026-08-22 in the approved SDK/widgets worktrees |
25
+
26
+ ## Applicability
27
+
28
+ | Condition ID | Status | Evidence or reason | Owned section |
29
+ | --- | --- | --- | --- |
30
+ | `feature.feature_nontrivial` | Applicable | `src/cc.ts`, `src/services/Queue.ts`, `src/services/EntryPoint.ts`, `src/services/AddressBook.ts`, `src/services/task/Task.ts` | Feasibility and risks |
31
+ | `feature.feature_interactions` | Applicable | `src/cc.ts` | Interaction and scenario matrix |
32
+ | `feature.touches_data_shapes` | Applicable | `src/types.ts` | Requested data and fields |
33
+ | `feature.backward_compat` | Applicable | `src/types.ts`, `src/index.ts` | Migration expectations |
34
+ | `feature.perf_critical` | N/A | The change adds no new request fan-out; it corrects cache eligibility for query variants. | Scale and performance |
35
+ | `feature.security_compliance` | N/A | Existing host-authenticated request ownership is unchanged and no credentials are added to list inputs. | Security and compliance |
36
+ | `feature.needs_rollout` | N/A | No SDK feature flag or staged runtime branch is introduced. | Rollout and feature controls |
37
+ | `feature.serviceability` | Applicable | `src/cc.ts`, `src/services/Queue.ts`, `src/services/EntryPoint.ts`, `src/services/AddressBook.ts` | Serviceability |
38
+ | `feature.doc_obligations` | Applicable | `ai-docs/contact-center-spec.md` | Documentation obligations |
39
+ | `feature.changes_ui` | N/A | The SDK has no user-visible screen or navigation ownership. | UI flow and design |
40
+ | `feature.changes_api` | Applicable | `src/cc.ts`, `src/services/Queue.ts`, `src/services/EntryPoint.ts`, `src/services/AddressBook.ts`, `src/services/task/Task.ts` | API contract delta |
41
+ | `feature.changes_events` | N/A | No event name, payload, producer, consumer, or delivery order changes. | Event contract delta |
42
+ | `feature.changes_public_api` | Applicable | `src/index.ts`, `src/types.ts` | Public API and semver impact |
43
+ | `feature.cross_package` | Applicable | `src/index.ts` | Cross-package impact |
44
+
45
+ ## Problem and goal
46
+
47
+ Consult/transfer list decisions were split across the SDK and widgets. Generic SDK query types exposed low-level request choices, while widgets always restricted buddy agents to Available, filtered queues after fetching them, rebuilt pagination metadata, and could independently affect presentation order. That produced inconsistent behavior between consumers.
48
+
49
+ The goal is to make the SDK the single owner of the default consult/transfer policy without adding parallel list methods or response signatures. The existing Queue method returns eligible full records, while the existing EntryPoint method maps profile-scoped dial-number rows to the established response wrapper. Queue, EntryPoint, and AddressBook request backend ordering, buddy-agent behavior is action-aware, CMS sort syntax is serialized correctly, and query variants that change results cannot reuse an incompatible cached page. Consumers render the response order and metadata without a second sort or filter.
50
+
51
+ ## Stakeholders and open questions
52
+
53
+ | Stakeholder | Need or decision | Status |
54
+ | --- | --- | --- |
55
+ | Contact Center agents | Destination eligibility and order are consistent across consumers. | Decided |
56
+ | SDK consumers | Reusable defaults without duplicating backend query knowledge. | Decided |
57
+ | Widget maintainers | Thin calls that pass only UI/runtime context. | Decided in the paired widgets delta |
58
+ | SDK maintainers | Existing list APIs remain the only queue and entry-point public methods; existing parameters provide overrides. | Decided |
59
+
60
+ There are no open product decisions for this delta.
61
+
62
+ ## Scope
63
+
64
+ ### In scope
65
+
66
+ - Put consult/transfer defaults on the existing queue and entry-point list methods.
67
+ - Map Consult versus Transfer to the correct buddy-agent state behavior.
68
+ - Default omitted buddy-agent and queue media context to telephony.
69
+ - Retain the existing queue/entry-point parameter and response wrappers; keep full Queue records, map EntryPoint dial-number rows to truthful `EntryPointRecord` fields, and retain compatible filter/sort overrides without exposing the fixed entry-point profile-scoping flag.
70
+ - Default EntryPoint requests to backend `entryPointName,ASC` and AddressBook requests to `name,ASC` while allowing callers to pass another `sortBy`/`sortOrder` pair.
71
+ - Serialize CMS ordering as `sort=<field>,<ORDER>`.
72
+ - Bypass the base pagination cache for every filter/view/shape flag that changes a result.
73
+ - Keep the existing queue and entry-point method signatures and preserve explicit buddy-agent state callers.
74
+ - Compute ordered, action-specific destination availability once on each Task and expose it through `TaskUIControls`, using Desktop Profile access, media, direction, and outbound queue-transfer capability.
75
+ - Keep direct Entry Point available for eligible voice transfers and translate its public destination type to the backend EPDN value inside `Task.transfer()`.
76
+
77
+ ### Out of scope
78
+
79
+ - Client-side sorting of agents, queues, or entry points.
80
+ - Changing backend order after a response is received.
81
+ - Adding parallel queue/entry-point APIs or projected destination response types.
82
+ - Changing generic queue ordering, address-book projection, events, authentication, retries, or metrics taxonomy.
83
+ - Adding a feature flag, data migration, commit, publication, or push.
84
+ - Adding a separate destination-policy fetch method that Task consumers must call before rendering.
85
+
86
+ ## Prior work and evidence
87
+
88
+ | Source | What it establishes | Decision or disposition |
89
+ | --- | --- | --- |
90
+ | `src/cc.ts` | The public façade keeps the established list method names/signatures and owns buddy-agent action policy. | Used |
91
+ | `src/types.ts`, `src/index.ts` | Existing queue/entry-point request and response types remain the public list contracts; entry-point rows expose the mapped dialled number as optional `number`. | Used |
92
+ | `src/services/Queue.ts` | The existing Queue path owns default query serialization and view flags. | Used |
93
+ | `src/services/EntryPoint.ts` | The existing EntryPoint path owns the desktop-profile dial-number query, field mapping, and backend ordering. | Used |
94
+ | `src/services/core/WebexRequest.ts` | The shared request wrapper forwards optional per-request headers needed by the dial-number endpoint while leaving other requests unchanged. | Used |
95
+ | `src/services/AddressBook.ts` | AddressBook owns its backend ordering default and caller override. | Used |
96
+ | `src/utils/PageCache.ts` | Cache eligibility must include every result- or shape-changing query option. | Used |
97
+ | `test/unit/spec/cc.ts` | Action mapping and thin delegation through the existing list methods are asserted. | Used |
98
+ | `test/unit/spec/services/Queue.ts`, `test/unit/spec/services/EntryPoint.ts`, `test/unit/spec/services/AddressBook.ts` | Default policy, existing-parameter overrides, CMS sort serialization, view flags, and cache behavior are asserted. | Used |
99
+ | `src/services/task/state-machine/uiControlsComputer.ts`, `src/services/task/types.ts` | Task UI controls are the existing SDK-owned decision surface and can carry ordered destination availability. | Used |
100
+ | `test/unit/spec/services/task/state-machine/uiControlsComputer.ts`, `test/unit/spec/services/task/TaskFactory.ts` | Profile/media/direction gating, outbound flag path, ordering, and factory propagation are asserted. | Used |
101
+ | `src/services/task/Task.ts`, `src/services/task/constants.ts`, `test/unit/spec/services/task/Task.ts` | Direct entry-point transfer routing is translated to the backend EPDN value and sent through the vteam transfer path. | Used |
102
+ | `docs/samples/contact-center/app.js` | The sample renders buddy-agent state labels and mapped entry-point numbers while using the existing list methods and Task destination controls. | Used |
103
+
104
+ ## Requirements
105
+
106
+ | ID | WHAT | WHY | Source evidence | Test or example evidence | Assumptions or gaps | Confidence |
107
+ | --- | --- | --- | --- | --- | --- | --- |
108
+ | `SDK-LIST-R-001` | Existing `getQueues` must retain `ContactServiceQueueSearchParams` and `ContactServiceQueuesResponse`, default to inbound active telephony queues ordered by backend name ascending with desktop-profile/agent/first-level views, avoid field projection, and honor defined caller-supplied existing parameters as overrides. Optional properties explicitly set to `undefined` retain defaults; explicit `false` flags and an explicit empty filter remain overrides. | Queue eligibility and ordering are consistent for ordinary calls without a new method or misleading projected/full-record type mismatch, while other consumers retain an explicit override path. Defined-only merging prevents a normally constructed optional-parameter object from accidentally disabling safe defaults. | `src/cc.ts`, `src/services/Queue.ts`, `src/types.ts` | `test/unit/spec/cc.ts`, `test/unit/spec/services/Queue.ts` | Backend honors the documented CMS query flags. | Present |
109
+ | `SDK-LIST-R-002` | Existing `getEntryPoints` must retain `EntryPointSearchParams` and `EntryPointListResponse`, query `/v3/dial-number` with organization/internal-data headers, fixed desktop-profile filtering, entry-point names, required mapping attributes, and backend `entryPointName,ASC`, then map each row to the existing `EntryPointRecord` as `id=entryPointId`, `name=entryPointName`, and optional `number=dialledNumber` without reordering. Caller-supplied compatible search, filter, attributes, and sort parameters remain available. | The visible entry-point number belongs to the dial-number mapping. Owning that mapping in the existing SDK method keeps consumers thin without exposing a parallel request or response type. | `src/cc.ts`, `src/services/EntryPoint.ts`, `src/services/config/constants.ts`, `src/services/core/WebexRequest.ts`, `src/types.ts` | `test/unit/spec/services/EntryPoint.ts`, `test/unit/spec/services/core/WebexRequest.ts` | The v3 response includes entry-point identifiers/names when `includeEntryPointName=true`. | Present |
110
+ | `SDK-LIST-R-003` | Buddy-agent requests using `Transfer` must add state `Available`; requests using `Consult` must omit the state filter; omitted action-based media defaults to telephony; both `BuddyAgents` branches reuse one private supported-media union. | Transfer and Consult have different eligible populations, and one media allowlist prevents action-based callers from issuing unsupported buddy requests without adding another public type. | `src/cc.ts`, `src/types.ts` | `test/unit/spec/cc.ts` | The backend determines the Consult-eligible states when state is omitted. | Present |
111
+ | `SDK-LIST-R-004` | Explicit buddy-agent state requests and existing queue/entry-point/address-book parameters must remain supported; caller-supplied filters and sort values override service defaults. | Existing SDK consumers need specialized behavior without a second list API. | `src/cc.ts`, `src/types.ts`, `src/services/Queue.ts`, `src/services/EntryPoint.ts`, `src/services/AddressBook.ts` | `test/unit/spec/cc.ts`, `test/unit/spec/services/Queue.ts`, `test/unit/spec/services/EntryPoint.ts`, `test/unit/spec/services/AddressBook.ts` | Existing callers that pass explicit `state` continue to use that branch. | Present |
112
+ | `SDK-LIST-R-005` | Queue, EntryPoint, and AddressBook services must serialize ordering as CMS `sort=<field>,<ORDER>`, not separate `sortBy`/`sortOrder` query keys. Queue and AddressBook default to `name,ASC`; EntryPoint maps the public default `name` field to backend `entryPointName,ASC`; a Queue `sortOrder` without `sortBy` uses `name`. | Correct wire syntax and SDK-owned defaults make backend ordering consistent and prevent a caller's explicit direction from being silently ignored. | `src/services/Queue.ts`, `src/services/EntryPoint.ts`, `src/services/AddressBook.ts` | `test/unit/spec/services/Queue.ts`, `test/unit/spec/services/EntryPoint.ts`, `test/unit/spec/services/AddressBook.ts` | None. | Present |
113
+ | `SDK-LIST-R-006` | PageCache must reject cache use when search, filter, attributes, a non-default/effective sort, or an enabled desktop-profile/provisioning/single-object flag is present. This includes a Queue `sortOrder` supplied without `sortBy`. Default Queue calls bypass simple-page caching because their eligibility filter and enabled views change the result set; profile-scoped EntryPoint requests are made directly without PageCache; AddressBook retains cache eligibility for its invariant default order. | The cache key does not encode result variants, so default policy requests and explicit query variants cannot safely share a page. | `src/utils/PageCache.ts`, `src/services/Queue.ts`, `src/services/EntryPoint.ts`, `src/services/AddressBook.ts` | `test/unit/spec/services/Queue.ts`, `test/unit/spec/services/EntryPoint.ts`, `test/unit/spec/services/AddressBook.ts` | Service-level behavior covers default and override cases. | Present |
114
+ | `SDK-LIST-R-007` | The SDK must not JavaScript-sort or reorder list response arrays. EntryPoint may rename/map fields row-for-row while preserving response order and pagination metadata. | Backend-requested order is authoritative, while field mapping must not alter list membership or order. | `src/cc.ts`, `src/services/Queue.ts`, `src/services/EntryPoint.ts` | `test/unit/spec/cc.ts`, `test/unit/spec/services/EntryPoint.ts` | The backend is the source of final row order. | Present |
115
+ | `SDK-LIST-R-008` | The existing `BuddyAgents` input and `TaskUIControls.consultTransferDestinations` field must carry action/media and ordered destination typing without exporting one-off aliases; queue and entry-point consumers continue to use the established request/response wrappers. `EntryPointRecord` must strongly type optional mapped `number`, while configuration-only fields absent from the mapped list are optional. | Public consumers need a truthful compile-time contract without extra public aliases, destination abstractions, response wrappers, or casts for the displayed entry-point number. | `src/types.ts`, `src/services/task/types.ts`, `src/index.ts`, `src/cc.ts` | `test/unit/spec/cc.ts`, `test/unit/spec/services/EntryPoint.ts`, `test/unit/spec/services/task/state-machine/uiControlsComputer.ts`, `package.json` | None. | Present |
116
+ | `SDK-LIST-R-009` | Buddy-agent, queue, and entry-point failures must preserve their existing measured/logged rejection semantics and must not return a synthetic successful list. | Callers need to distinguish a real empty result from a transport or backend failure. | `src/cc.ts`, `src/services/Queue.ts`, `src/services/EntryPoint.ts` | `test/unit/spec/cc.ts`, `test/unit/spec/services/Queue.ts`, `test/unit/spec/services/EntryPoint.ts` | Consumer UI fallback behavior remains outside the SDK. | Present |
117
+ | `SDK-LIST-R-010` | AddressBook must request backend `name,ASC` ordering by default and must accept caller-supplied `sortBy`/`sortOrder` overrides without a consult-specific façade method. | Widgets and other ordinary consumers receive backend-ordered dial numbers out of the box, while consumers with another requirement retain control. | `src/services/AddressBook.ts` | `test/unit/spec/services/AddressBook.ts` | Backend honors the documented CMS sort value. | Present |
118
+ | `SDK-LIST-R-011` | Non-default queue media eligibility must be supplied through the existing RSQL `filter` parameter; the SDK never interpolates an unvalidated media string into a filter. | Reusing the established filter contract avoids a second media-bearing signature and removes the prior filter-injection path. | `src/services/Queue.ts`, `src/types.ts` | `test/unit/spec/services/Queue.ts` | Consumers that construct explicit RSQL filters remain responsible for supplying valid backend syntax. | Present |
119
+ | `SDK-LIST-R-012` | Every Task must expose `uiControls.consultTransferDestinations` with ordered `consult` and `transfer` arrays. Order is Agent, Queue, Dial Number, Entry Point after gating: profile `NONE` removes agent/queue/entry point; voice Consult queue requires `allowConsultToQueue`; voice Transfer queue requires inbound direction or outbound plus `interaction.callProcessingDetails.outdialTransferToQueueEnabled === true`; unknown voice direction does not allow queue Transfer; digital exposes only allowed agent/queue categories. | All consumers need the same destination decision out of the box, without reading raw profile flags, interpreting task payload paths, or calling another policy API. | `src/cc.ts`, `src/services/task/TaskFactory.ts`, `src/services/task/types.ts`, `src/services/task/state-machine/uiControlsComputer.ts` | `test/unit/spec/cc.ts`, `test/unit/spec/services/task/TaskFactory.ts`, `test/unit/spec/services/task/state-machine/uiControlsComputer.ts` | Consumers may hide an SDK-allowed category for host UX, but cannot enable one the SDK omitted. | Present |
120
+ | `SDK-LIST-R-013` | A direct `Task.transfer()` to the public `entryPoint` destination must remain available for eligible voice tasks, translate internally to backend destination type `entrypointDialNumber`, and use `vteamTransfer`; callers continue to pass the selected entry-point identifier and do not perform backend translation. | Entry-point transfer is a supported vteam operation, while sending the public value unchanged through `blindTransfer` selects the wrong backend operation and makes SDK-owned controls advertise a failing action. | `src/services/task/Task.ts`, `src/services/task/constants.ts`, `src/services/task/types.ts` | `test/unit/spec/services/task/Task.ts` | The existing entry-point identifier remains a valid fallback when no analyzer identifier is exposed, matching the established transfer policy. | Present |
121
+ | `SDK-LIST-R-014` | The Contact Center sample must treat a present empty Task destination array as an explicit “no destinations” decision by clearing and disabling the selector; only a missing/undefined control uses backward-compatible sample defaults. | An empty SDK policy result must not be replaced with categories the Task explicitly disallowed, while the sample still needs to run against older SDK builds that do not expose the field. | `docs/samples/contact-center/app.js` | Manual sample flow | The sample has no dedicated DOM unit suite. | Present |
122
+
123
+ ## Defect context (when applicable)
124
+
125
+ - Observed versus expected behavior: widgets and SDK callers could construct different destination requests, the services serialized sort with keys the CMS list API does not consume, and cache eligibility ignored view/shape flags; expected behavior is one SDK-owned default policy and unchanged backend response order.
126
+ - Reproduction and environment: issue Consult and Transfer destination requests for the same task media and compare query parameters and results across SDK consumers.
127
+ - Regression range or last known good state: unknown; the existing APIs and older query serialization predate the corrected defaults.
128
+ - Severity, frequency, and workaround: user-visible whenever eligibility/order differs; consumers could manually duplicate flags, but that perpetuates the ownership defect.
129
+ - Diagnostic evidence: `src/cc.ts`, `src/services/Queue.ts`, `src/services/EntryPoint.ts`, `src/utils/PageCache.ts`.
130
+
131
+ ## MODIFIED Requirements
132
+
133
+ ### MOD-001 — Contact Center façade policy (`CONTACT_CENTER-R-003`)
134
+
135
+ - **WHAT**: Retain the existing `getQueues`, `getEntryPoints`, and `getBuddyAgents` method names. Buddy-agent behavior is action-aware; Queue retains its parameter/full-record response and owns telephony eligibility/views/order, while EntryPoint retains its parameter/response wrapper and owns the profile-scoped dial-number query, row mapping, order, and cache policy.
136
+ - **WHY**: A stable public owner prevents every UI consumer from reconstructing eligibility and query details.
137
+ - **Evidence:** `src/cc.ts`, `src/types.ts`, `src/index.ts`, `test/unit/spec/cc.ts`.
138
+ - **Acceptance:** Façade tests cover Consult, Transfer, and unchanged existing-method delegation; service tests cover default policy, explicit existing-filter overrides, and exact responses.
139
+
140
+ ### MOD-002 — Direct REST list services (`SERVICES-R-002`, `SERVICES-R-007`)
141
+
142
+ - **WHAT**: Queue, EntryPoint, and AddressBook must serialize CMS sorting as a combined `sort` value and honor explicit compatible caller overrides. Queue must apply its defaults when optional properties are absent or `undefined`, while retaining explicit `false` and empty-filter overrides. Queue and AddressBook default to `name,ASC`; EntryPoint requests profile-scoped `/v3/dial-number` rows with `entryPointName,ASC` and maps them into the established response wrapper while retaining direct HTTP completion/error semantics.
143
+ - **WHY**: SDK defaults are effective only when service wire parameters match the backend contract.
144
+ - **Evidence:** `src/services/Queue.ts`, `src/services/EntryPoint.ts`, `src/services/AddressBook.ts`, `test/unit/spec/services/Queue.ts`, `test/unit/spec/services/EntryPoint.ts`, `test/unit/spec/services/AddressBook.ts`.
145
+ - **Acceptance:** Service tests assert Queue/AddressBook `sort=name,ASC`, EntryPoint `sort=entryPointName,ASC`, Queue defaults with undefined optional fields, explicit Queue overrides, required views/mapping fields, and row-for-row EntryPoint mapping.
146
+
147
+ ### MOD-003 — Buddy-agent request contract (`AGENT-R-003`)
148
+
149
+ - **WHAT**: Preserve the existing `BuddyAgents` options object and correlated request/response contract while allowing its optional `action` field to derive state from `Consult` or `Transfer`. `mediaType` defaults to telephony, and an explicit `state` takes precedence over the action default.
150
+ - **WHY**: Eligibility changes must not alter AQM settlement or invent UI-side filtering.
151
+ - **Evidence:** `src/cc.ts`, `src/services/agent/index.ts`, `test/unit/spec/cc.ts`, `test/unit/spec/services/agent/index.ts`.
152
+ - **Acceptance:** Transfer sends `Available`; Consult sends no state; explicit state callers remain typed and supported.
153
+
154
+ ### MOD-004 — Query-aware cache eligibility (`UTILS-R-001`, `UTILS-R-006`)
155
+
156
+ - **WHAT**: Treat enabled profile/response-shape flags and non-default sorts as cache-disqualifying inputs. Existing Queue requests bypass cache through their fixed filters/views, EntryPoint makes its profile-scoped requests directly without PageCache, and default `name,ASC` AddressBook pages remain cache-eligible because that ordering is invariant for its base cache key.
157
+ - **WHY**: A page keyed only by scope/page/pageSize cannot safely represent query variants, but it can safely represent one invariant default order.
158
+ - **Evidence:** `src/utils/PageCache.ts`, `src/services/Queue.ts`, `src/services/EntryPoint.ts`, `test/unit/spec/services/Queue.ts`, `test/unit/spec/services/EntryPoint.ts`.
159
+ - **Acceptance:** Two identical Queue view-filtered or custom-sort calls make two backend requests; EntryPoint always makes the requested backend call; repeated default-sorted AddressBook pagination remains cache-eligible.
160
+
161
+ ### MOD-005 — Direct entry-point transfer routing (`TASK-R-003`, `TASK-R-009`)
162
+
163
+ - **WHAT**: Keep Entry Point in eligible voice Transfer destination controls. When `Task.transfer()` receives the public `entryPoint` destination, translate it internally to `entrypointDialNumber` and invoke `contact.vteamTransfer`; Queue remains on `vteamTransfer`, while Agent and Dial Number remain on `blindTransfer`.
164
+ - **WHY**: Consumers must be able to follow Task controls directly without knowing backend routing values, and supported entry-point transfers must use the same vteam operation as the established transfer policy.
165
+ - **Evidence:** `src/services/task/Task.ts`, `src/services/task/constants.ts`, `src/services/task/types.ts`, `test/unit/spec/services/task/Task.ts`.
166
+ - **Acceptance:** Task tests assert the exact EPDN vteam payload, no blind-transfer call, and unchanged Queue/Agent dispatch.
167
+
168
+ ## Acceptance criteria
169
+
170
+ - [x] Transfer buddy lookup sends state `Available`; Consult omits state; action-based media defaults to telephony (`MOD-003`, `SDK-LIST-R-003`).
171
+ - [x] Existing `getQueues` sends the default inbound/active/telephony filter, backend name ascending order, desktop-profile, agent, and first-level views without a field projection (`MOD-001`, `MOD-002`, `SDK-LIST-R-001`).
172
+ - [x] Queue optional fields set to `undefined` retain safe defaults, while explicit `false` and an explicit empty filter remain overrides (`MOD-002`, `SDK-LIST-R-001`).
173
+ - [x] Existing `getEntryPoints` requests desktop-profile-filtered `/v3/dial-number` mappings with required headers, entry-point names, and backend `entryPointName,ASC`, then exposes each dialled number as `EntryPointRecord.number` without changing row order (`SDK-LIST-R-002`, `SDK-LIST-R-007`).
174
+ - [x] Caller-supplied existing queue filters override its telephony default; compatible EntryPoint filters/sorts override its v3 mapping defaults while profile scoping remains fixed (`SDK-LIST-R-001`, `SDK-LIST-R-002`, `SDK-LIST-R-011`).
175
+ - [x] AddressBook sends backend name ascending order by default and honors a caller-supplied descending override (`MOD-002`, `SDK-LIST-R-004`, `SDK-LIST-R-010`).
176
+ - [x] Queue, EntryPoint, and AddressBook serialize CMS ordering as the combined `sort` query value (`MOD-002`, `SDK-LIST-R-005`).
177
+ - [x] Queue `sortOrder` without `sortBy` serializes as `sort=name,<ORDER>` and bypasses the simple-page cache (`SDK-LIST-R-005`, `SDK-LIST-R-006`).
178
+ - [x] Default Queue policy and other view/filter/shape/custom-sort requests bypass PageCache, EntryPoint makes its profile-scoped requests directly, and default-sorted AddressBook pages remain cacheable (`MOD-004`, `SDK-LIST-R-006`).
179
+ - [x] No SDK façade or service sorts returned arrays in JavaScript (`SDK-LIST-R-007`).
180
+ - [x] Existing queue and entry-point methods retain their response wrappers; `EntryPointRecord` additively types mapped `number` and marks configuration-only fields optional because the v3 mapping response does not provide them (`SDK-LIST-R-008`).
181
+ - [x] The Contact Center sample uses the existing Task/list surfaces, labels buddy-agent availability, and displays `EntryPointRecord.number` when present (`SDK-LIST-R-002`, `SDK-LIST-R-008`).
182
+ - [x] The Contact Center sample clears and disables its destination selector for a present empty Task destination array, while missing controls retain backward compatibility (`SDK-LIST-R-014`).
183
+ - [x] Direct entry-point transfer remains SDK-advertised for eligible voice tasks and is sent through `vteamTransfer` as `entrypointDialNumber`, with no widgets-side translation (`MOD-005`, `SDK-LIST-R-013`).
184
+ - [x] The package builds and the complete Contact Center unit and style suites pass (`SDK-LIST-R-008`).
185
+
186
+ ## Scenarios and applicable change views
187
+
188
+ | Scenario | Actor | Preconditions | Expected behavior | Failure or boundary behavior | Requirements |
189
+ | --- | --- | --- | --- | --- | --- |
190
+ | Consult buddy agents | SDK consumer | `action=Consult` | Telephony defaults when absent; state is omitted; backend order is preserved. | Request rejection is measured/logged and rethrown. | `SDK-LIST-R-003`, `SDK-LIST-R-007` |
191
+ | Transfer buddy agents | SDK consumer | `action=Transfer` | State `Available` is sent for the selected media. | Explicit state and action cannot be combined by the public type. | `SDK-LIST-R-003`, `SDK-LIST-R-008` |
192
+ | Queue list | SDK consumer | Existing method called with page/search and optional filter override | SDK applies the default telephony policy and returns full records unchanged; an explicit existing filter overrides eligibility. | HTTP failure is propagated without a synthetic page. | `SDK-LIST-R-001`, `SDK-LIST-R-007`, `SDK-LIST-R-011` |
193
+ | Entry-point list | SDK consumer | Existing method called with page/search and optional compatible overrides | SDK fetches desktop-profile dial-number mappings, preserves backend order/meta, and returns `{id, name, number?}` rows through `EntryPointListResponse`. | HTTP failure is propagated without a synthetic page. | `SDK-LIST-R-002`, `SDK-LIST-R-007`, `SDK-LIST-R-008`, `SDK-LIST-R-009` |
194
+ | Dial-number list | SDK consumer | AddressBook page/search supplied | AddressBook applies backend `name,ASC` by default and returns the response unchanged. | A custom sort overrides the default and bypasses the default-order cache. | `SDK-LIST-R-010` |
195
+ | Specialized list consumer | SDK consumer | Uses an existing list method with explicit parameters | Explicit filter/sort/profile inputs override defaults. | No parallel consult/transfer method or projected response type is required. | `SDK-LIST-R-004`, `SDK-LIST-R-005` |
196
+ | Direct entry-point transfer | SDK consumer | Voice Task exposes Entry Point in the Transfer destination array | `Task.transfer({to, destinationType: 'entryPoint'})` sends `{to, destinationType: 'entrypointDialNumber'}` through `vteamTransfer`. | Vteam rejection is measured and rethrown; `blindTransfer` is not invoked. | `SDK-LIST-R-012`, `SDK-LIST-R-013` |
197
+ | Sample receives an empty destination array | Sample user | Task exposes the requested action with `[]` | Destination selector is cleared and disabled. | Missing/undefined destination controls use the sample's compatibility defaults. | `SDK-LIST-R-014` |
198
+
199
+ ### Interaction and scenario matrix
200
+
201
+ | Context or interacting state | Trigger | Expected result | Invalid or conflicting result | Requirements |
202
+ | --- | --- | --- | --- | --- |
203
+ | Consult + agent | Action request | No state filter | Applying Transfer-only `Available` | `SDK-LIST-R-003` |
204
+ | Transfer + agent | Action request | `state=Available` | Returning idle agents through an omitted state filter | `SDK-LIST-R-003` |
205
+ | Queue + social media | Existing list request with filter override | Caller supplies `channelType==SOCIAL_CHANNEL` through `filter` | Adding a second media-bearing method signature | `SDK-LIST-R-001`, `SDK-LIST-R-011` |
206
+ | View-filtered Queue or profile-scoped EntryPoint | Repeated page request | Backend called for each request | Simple-page cache hit | `SDK-LIST-R-006` |
207
+ | Existing Queue or AddressBook | Sort omitted | Backend receives `sort=name,ASC` | Consumer must provide the default itself | `SDK-LIST-R-005`, `SDK-LIST-R-010` |
208
+ | Existing EntryPoint | Sort omitted | Backend receives `sort=entryPointName,ASC` and mapped rows remain in that order | Widget sorts or requests the mapping itself | `SDK-LIST-R-002`, `SDK-LIST-R-005`, `SDK-LIST-R-007` |
209
+ | Existing Queue, EntryPoint, or AddressBook | Custom sort supplied | Backend receives the requested field/order | SDK overwrites the caller's explicit behavior | `SDK-LIST-R-004`, `SDK-LIST-R-010` |
210
+ | Backend result | Response received | Array and metadata returned in backend order | JavaScript `.sort()` or consumer-specific reorder | `SDK-LIST-R-007` |
211
+ | Voice Transfer + entry point | Destination selected | SDK maps `entryPoint` to backend `entrypointDialNumber` and calls `vteamTransfer` | Sending `entryPoint` through `blindTransfer` or hiding the supported category | `SDK-LIST-R-013` |
212
+ | Sample + present empty controls | Task selection changes | Selector has no options and is disabled | Sample substitutes legacy defaults for an explicit empty array | `SDK-LIST-R-014` |
213
+
214
+ ### API contract delta
215
+
216
+ | API or operation | Change | Consumer impact | Compatibility expectation | Canonical definition |
217
+ | --- | --- | --- | --- | --- |
218
+ | Buddy-agent input | Add optional `action` to the existing options object and make `mediaType` optional with a telephony default. | Consumers may pass Consult/Transfer instead of choosing state. | Additive public option; explicit-state callers remain supported and take precedence. | `src/types.ts` |
219
+ | Existing queue list | Apply the telephony filter, profile views, and `name,ASC` by default. | Thin clients call `getQueues`; other consumers use existing parameters for overrides. | Intentional default correction; method and response signature unchanged. | `src/cc.ts`, `src/services/Queue.ts` |
220
+ | Existing entry-point list | Fetch desktop-profile `/v3/dial-number` mappings with the required organization/internal-data headers, request entry-point names, map fields row-for-row, and use `entryPointName,ASC` by default. | Thin clients call `getEntryPoints` and receive the displayed number without joining another endpoint. | Intentional default correction; method and response wrapper unchanged. | `src/cc.ts`, `src/services/EntryPoint.ts`, `src/services/config/constants.ts`, `src/services/core/WebexRequest.ts` |
221
+ | `EntryPointRecord` | Add optional mapped `number`; make configuration-only `type`, `isActive`, and `orgId` optional for truthful mapped-list typing. | Consumers can render the dialled number without a cast and cannot assume absent configuration fields. | Additive field with a type-correctness adjustment; no new response wrapper. | `src/types.ts` |
222
+ | Task destination controls | Add ordered `consultTransferDestinations.consult` and `.transfer` arrays to `TaskUIControls`. | Task consumers render availability directly; no separate policy call or raw profile injection is needed. | Additive public field using the existing destination values; no new standalone public alias. | `src/services/task/types.ts`, `src/services/task/state-machine/uiControlsComputer.ts`, `src/index.ts` |
223
+ | Existing `Task.transfer` entry-point input | Correct internal transport and backend destination translation. | Consumers keep passing `{to, destinationType: 'entryPoint'}` from the Task control array. | Behavioral bug fix; no method or public payload signature change. | `src/services/task/Task.ts`, `src/services/task/constants.ts` |
224
+
225
+ ### Public API and semver impact
226
+
227
+ | Export or entry point | Change | Affected consumers | Required version change | Deprecation or migration |
228
+ | --- | --- | --- | --- | --- |
229
+ | Existing `getQueues` / `getEntryPoints` | Default request behavior changes; signatures do not | Widgets and other SDK consumers | Behavioral semver review | Pass compatible existing filters/sorts when different behavior is required; entry-point profile scoping remains SDK-owned. |
230
+ | `BuddyAgents` | Add optional action-based defaults to the existing options object while retaining explicit state | Existing and new consumers | Minor | Existing explicit-state calls remain valid and override action defaults. |
231
+ | `TaskUIControls` | Add inline ordered, action-specific destination availability using existing destination values | Task UI consumers | Minor | Read the matching action array; first item is the default category. |
232
+ | `Task.transfer` | Route the existing public `entryPoint` value through vteam transfer as backend `entrypointDialNumber` | Existing voice-task consumers | Patch/behavioral correction | No caller migration; backend translation is SDK-owned. |
233
+ | `EntryPointRecord` | Add optional mapped `number`; configuration-only fields become optional | Entry-point list consumers | Behavioral/type-contract review | Render `number` when present and handle configuration-only fields as optional. |
234
+
235
+ ### Cross-package impact
236
+
237
+ | Package | Change | Dependency direction | Release sequencing | Owner |
238
+ | --- | --- | --- | --- | --- |
239
+ | `@webex/contact-center` | Owns action/default/filter/order/cache policy and Task destination visibility/order decisions. | SDK → consumers | Build/release first. | SDK maintainers |
240
+ | `@webex/cc-store` | Delegates entry points directly to the existing SDK method; uses the existing queue `filter` parameter only for a non-telephony active task. | store → SDK | Consume a compatible SDK release. | Widgets maintainers |
241
+ | `@webex/cc-task` and `@webex/cc-components` | Supply action and render results. | UI → store → SDK | Release after compatible store/SDK. | Widgets maintainers |
242
+
243
+ ## Contracts delta
244
+
245
+ **Provides — MODIFIED:** The package keeps the existing queue, entry-point, buddy-agent, and Task transfer methods. Queue retains its established request/full-response signature and telephony defaults; EntryPoint retains its request/response wrapper while mapping desktop-profile dial-number rows to typed `{id, name, number?}` records in backend order; buddy agents accept action-aware input through `BuddyAgents`; `TaskUIControls` exposes inline ordered action-specific destination availability; direct entry-point transfer uses SDK-owned EPDN/vteam translation without changing the public payload.
246
+
247
+ **Requires — MODIFIED:** Queue, EntryPoint, and AddressBook services require CMS list endpoints to honor the combined sort value. Queue requires its profile/agent/first-level views; EntryPoint requires `/v3/dial-number` to honor the organization/internal-data headers, desktop-profile filtering, `includeEntryPointName`, and mapping attributes. Direct entry-point transfer requires the WCC vteam transfer operation to accept the established `entrypointDialNumber` destination and selected entry-point identifier. The SDK continues to rely on host-authenticated Webex requests and backend response ordering.
248
+
249
+ No event contract changes.
250
+
251
+ ## Success and guardrail metrics
252
+
253
+ | Metric | Baseline | Target | Measurement source |
254
+ | --- | --- | --- | --- |
255
+ | Consumers that must recreate the default queue/entry-point policy | Widgets did | 0 for ordinary existing-method calls | `src/services/Queue.ts`, `src/services/EntryPoint.ts` |
256
+ | JavaScript-side destination sorts in the changed SDK path | 0 | 0 | `src/cc.ts`, `src/services/Queue.ts`, `src/services/EntryPoint.ts` |
257
+ | Cache hits for view/filter/shape query variants | Possible | 0 | `test/unit/spec/services/Queue.ts`, `test/unit/spec/services/EntryPoint.ts` |
258
+ | Contact Center unit failures | Unknown before change | 0 | `test/unit/spec` |
259
+ | Contact Center build/style errors | Unknown before change | 0 | Package build and style commands |
260
+
261
+ ## Requested data and fields
262
+
263
+ | Entity or payload | Requested field or shape | Purpose | Ownership | Privacy, retention, or compatibility constraint |
264
+ | --- | --- | --- | --- | --- |
265
+ | Buddy-agent input | Existing options object with optional `action`, `mediaType`, and explicit `state`; explicit state takes precedence | Derive Consult/Transfer eligibility without a parallel public input type. | SDK public type | No credential or persistent data. |
266
+ | Queue search input | Existing page, page size, search, filter, sort, and profile parameters | Consumer-controlled pagination plus optional default overrides. | Existing SDK public type | No second media-bearing request type. |
267
+ | Queue backend query | Default inbound/active/telephony filter, name ascending, desktop-profile/agent/first-level views, and no field projection | Full queue result using the default list policy. | Queue service | Fixed filter/views bypass simple-page caching. |
268
+ | Entry-point backend query | `/v3/dial-number`, `X-ORGANIZATION-ID`, `x-ignore-internal-data=false`, `desktopProfileFilter=true`, `includeEntryPointName=true`, required mapping attributes, and `entryPointName,ASC` | Return profile-scoped EP-DN rows with the visible dialled number. | EntryPoint service and shared WebexRequest wrapper | The service does not use PageCache for these profile-scoped requests. |
269
+ | Entry-point response row | `id=entryPointId`, `name=entryPointName`, optional `number=dialledNumber` | Let consumers route by entry-point ID and display the mapped dialled number without a cast or second request. | `EntryPointRecord` public type | Mapping preserves response order and pagination metadata. |
270
+ | Direct entry-point transfer payload | Caller-selected `to`; public `entryPoint` translated internally to `entrypointDialNumber` | Invoke the supported vteam transfer operation without consumer-side backend knowledge. | Task service | Translation is transport-only; metrics retain the caller-facing destination type and no new public field is required. |
271
+ | AddressBook backend query | Existing caller-selected fields plus name ascending by default | Backend-ordered dial numbers without a specialized façade. | AddressBook service | A non-default sort bypasses the default-order cache. |
272
+
273
+ ## Impacted domains
274
+
275
+ | Repository or module | Impact | Owner |
276
+ | --- | --- | --- |
277
+ | `src` | Public façade and exports | SDK maintainers |
278
+ | `src/services` | Queue/EntryPoint/AddressBook wire query construction | SDK maintainers |
279
+ | `src/services/agent` | Existing correlated buddy-agent operation receives façade-derived state | SDK maintainers |
280
+ | `src/services/task` | Direct entry-point transfer dispatch and backend destination translation | SDK maintainers |
281
+ | `src/utils` | Cache eligibility for query variants | SDK maintainers |
282
+ | Webex widgets repository | Thin consumer of the new defaults | Widgets maintainers |
283
+
284
+ ## Feasibility and risks
285
+
286
+ | Risk or assumption | Evidence | Mitigation or decision owner |
287
+ | --- | --- | --- |
288
+ | CMS ignores ordering when encoded as legacy separate keys. | `src/services/Queue.ts`, `src/services/EntryPoint.ts` | Use and test combined `sort=<field>,<ORDER>` serialization. |
289
+ | Simple cache returns a page created under a different view. | `src/utils/PageCache.ts` | Make every result/shape flag cache-disqualifying and retain repeated-call tests. |
290
+ | New EntryPoint/AddressBook ordering defaults affect generic callers. | `src/services/EntryPoint.ts`, `src/services/AddressBook.ts` | Make the correction explicit, retain caller overrides, and test both default and custom order. |
291
+ | A consumer re-sorts backend results. | `test/unit/spec/cc.ts` | Return the delegated response unchanged and document backend order as authoritative. |
292
+ | Direct entry-point transfer is sent to the blind-transfer operation or with the public destination literal. | `src/services/task/Task.ts`, established transfer-policy behavior | Route through `vteamTransfer`, translate to `entrypointDialNumber`, and assert the exact payload. |
293
+ | Entry-point configuration records do not contain the visible dialled number, and widget runtime returned no provisional `dbId`. | The backend `/v3/dial-number` contract returns `dialledNumber`, `entryPointId`, and `entryPointName`. | Move the EP-DN request/mapping into existing `getEntryPoints`, type `number`, and keep widget rendering declarative. |
294
+
295
+ ## Error Matrix
296
+
297
+ | Failure | SDK behavior | Consumer-visible result | Evidence |
298
+ | --- | --- | --- | --- |
299
+ | Buddy-agent AQM rejection | Record failure context and rethrow. | Promise rejects; no synthetic agent list. | `src/cc.ts`, `test/unit/spec/cc.ts` |
300
+ | Queue HTTP rejection | Service metrics/logging remain active and the error propagates. | Promise rejects; no synthetic paginated result. | `src/services/Queue.ts`, `test/unit/spec/services/Queue.ts` |
301
+ | Entry-point HTTP rejection | Service metrics/logging remain active and the error propagates. | Promise rejects; no synthetic paginated result. | `src/services/EntryPoint.ts`, `test/unit/spec/services/EntryPoint.ts` |
302
+ | Missing action-based media | Default to telephony. | Valid request with predictable channel. | `src/cc.ts`, `test/unit/spec/cc.ts` |
303
+ | Non-default queue media eligibility | Consumer supplies a complete allowlisted RSQL value through the existing `filter` field; the SDK performs no media-string interpolation. | Existing queue method returns matching records or propagates the backend error. | `src/services/Queue.ts`, service tests |
304
+ | Direct entry-point vteam transfer rejection | Preserve existing Task transfer error normalization, failure metrics, and rethrow semantics. | `Task.transfer()` rejects; no fallback blind-transfer request is made. | `src/services/task/Task.ts`, `test/unit/spec/services/task/Task.ts` |
305
+
306
+ ## Resilience
307
+
308
+ - Existing methods make one delegated list request and add no retry or request fan-out.
309
+ - Queue, EntryPoint, and AddressBook callers use compatible explicit existing parameters when they require non-default behavior.
310
+ - View/filter/shape queries bypass cache rather than risk stale or cross-policy results.
311
+ - Errors remain caller-visible; the SDK does not manufacture an empty success response.
312
+
313
+ ## Observability
314
+
315
+ - Existing buddy-agent success/failure metrics retain media and derived state context plus count, without logging agent identities.
316
+ - Existing Queue and EntryPoint request/success/failure metrics continue to cover the default and overridden calls.
317
+ - Existing Task transfer success/failure metrics continue to report the caller-facing entry-point destination while transport uses the backend EPDN value.
318
+ - No new metric taxonomy, PII-bearing log, credential log, trace, or alert is introduced.
319
+
320
+ ## Operations
321
+
322
+ - Build and run the complete Contact Center unit suite and style check before publishing.
323
+ - Release the SDK before or with widgets that require the corrected existing-method defaults and Task controls.
324
+ - Rollback is a coordinated package-version/code rollback; no persisted state, schema, or cache migration is required.
325
+
326
+ ## Migration expectations
327
+
328
+ - Compatibility: list method names and response wrappers remain unchanged; explicit buddy-agent state remains supported; optional `EntryPointRecord.number` is additive and configuration-only entry-point fields are now optional. Queue/AddressBook request `name,ASC`; EntryPoint requests mapped, profile-scoped `entryPointName,ASC` rows while retaining compatible filter/sort overrides.
329
+ - Data or consumer transition: thin consumers continue using `getQueues` and `getEntryPoints`; consumers needing different behavior pass existing query overrides.
330
+ - Coexistence period: no parallel list surface exists.
331
+ - Completion and rollback outcome: consumers no longer own the default consult/transfer policy; rollback restores prior calls without data cleanup.
332
+
333
+ ## Serviceability
334
+
335
+ | Signal or support surface | Required change | Consumer or operator | Acceptance evidence |
336
+ | --- | --- | --- | --- |
337
+ | Buddy-agent operational metrics | Report derived action state and media without identities. | SDK maintainers | `test/unit/spec/cc.ts` |
338
+ | Queue request metrics/logs | Preserve existing request success/failure coverage for default and overridden calls. | SDK maintainers | `test/unit/spec/services/Queue.ts` |
339
+ | Entry-point request metrics/logs | Preserve existing request success/failure coverage for default and overridden calls. | SDK maintainers | `test/unit/spec/services/EntryPoint.ts` |
340
+
341
+ ## Documentation obligations
342
+
343
+ - This approved delta modifies `CONTACT_CENTER-R-003`, `SERVICES-R-002`, `SERVICES-R-007`, `AGENT-R-003`, `UTILS-R-001`, and `UTILS-R-006` without overwriting protected canonical specs.
344
+ - Direct entry-point routing additionally modifies `TASK-R-003` and `TASK-R-009` through this approved MODIFIED delta; the protected Task canonical spec remains unchanged until a future reconciliation/promotion.
345
+ - The paired widgets feature spec must reference this SDK delta as the owner of queue eligibility/order/profile views and entry-point dial-number mapping/order; widgets delegate entry points without media filtering and may pass a queue filter for an active non-telephony task.
346
+ - A future canonical-spec promotion must fold this delta into the routed module specs and reconcile the delta path rather than duplicate the requirements.
347
+
348
+ ## Decision and change log
349
+
350
+ | Date | Decision or change | Rationale | Owner |
351
+ | --- | --- | --- | --- |
352
+ | 2026-08-21 | Replaced provisional `dbId` with typed `EntryPointRecord.number` populated from the backend `/v3/dial-number` mapping, and kept the existing `getEntryPoints` method/response wrapper. | Runtime testing showed no `dbId`; the dialled number belongs to the EP-DN mapping, and consumers should not join or reinterpret backend data. | Developer + Codex |
353
+ | 2026-08-21 | Made Queue defaults resilient to optional properties explicitly set to `undefined`, retained explicit false/empty overrides, and made the sample honor a present empty destination array. | Common object-building patterns must not silently disable safe SDK defaults, and an explicit Task policy decision must not be replaced by sample fallback categories. | Developer + Codex |
354
+ | 2026-08-21 | Superseded the provisional optional `EntryPointRecord.dbId` experiment. | Runtime validation established that the displayed field is `dialledNumber` from the EP-DN mapping, now exposed as `number`. | Developer + Codex |
355
+ | 2026-08-20 | Kept Entry Point available for eligible voice transfers and corrected `Task.transfer()` to use vteam routing with internal `entrypointDialNumber` translation. | The backend transfer policy supports direct entry-point transfer; hiding it would remove valid functionality, while consumers should not know the backend EPDN literal. | Developer + Codex |
356
+ | 2026-08-19 | Kept action/media typing inside `BuddyAgents`, inlined the destination arrays on `TaskUIControls`, removed the new root aliases, and removed `dbId` additions from queue/entry-point records. | The established methods and types already express the required behavior; consumers do not need standalone aliases or an unused record field. | Developer + Codex |
357
+ | 2026-08-19 | Approved this exact MODIFIED delta path. | Preserve protected canonical specs while maintaining spec-currency with the implementation. | Developer |
358
+ | 2026-08-19 | Assigned all reusable eligibility, query, ordering, and cache decisions to the SDK. | Keep widgets thin and prevent cross-consumer behavior drift. | Developer + Codex |
359
+ | 2026-08-19 | Made backend response order authoritative and prohibited SDK-side JavaScript sorting. | One backend ordering decision must reach every consumer unchanged. | Developer + Codex |
360
+ | 2026-08-19 | Moved EntryPoint and AddressBook `name,ASC` ordering to service defaults and removed the specialized dial-number façade. | Widgets must work without supplying SDK-owned decisions; other consumers can pass explicit sort overrides. | Developer + Codex |
361
+ | 2026-08-19 | Removed the specialized queue/entry-point methods and destination response/options types and kept default policy on existing `getQueues`/`getEntryPoints` with existing overrides. | Consumers should keep established method signatures; a parallel list abstraction adds needless public surface and projection complexity. The later EP-DN correction retained the response wrapper while mapping truthful fields. | Developer + Codex |
362
+ | 2026-08-19 | Put ordered Consult/Transfer destination availability directly on every Task's `uiControls` instead of adding `getConsultTransferDestinationPolicy`. | The Task already owns UI decisions and live interaction data, so consumers should not make a second request or reproduce profile/media/direction rules. | Developer + Codex |
@@ -0,0 +1,117 @@
1
+ # Feature Spec — Generated Spec Conformance and Fidelity Remediation
2
+
3
+ > Start here → package root [`AGENTS.md`](../../../../AGENTS.md) · router [`SPEC_INDEX.md`](../../../SPEC_INDEX.md) · system [`ARCHITECTURE.md`](../../../ARCHITECTURE.md). This is a documentation-only protected-spec delta. It authorizes canonical documentation corrections but no runtime, test, or manifest change.
4
+
5
+ ## Metadata
6
+
7
+ | Field | Value |
8
+ |---|---|
9
+ | Feature / ticket key | `CC-SDD-CONFORMANCE-FIDELITY-20260709` |
10
+ | Title | Generated module-spec conformance and source-fidelity remediation |
11
+ | Status | applied; generator-side source fidelity, conformance, and coverage pass; independent validation pending |
12
+ | Change class | documentation-only MODIFIED conformance and fidelity correction |
13
+ | created_by / approved_by / date | Codex generator / developer / 2026-07-09 |
14
+ | Generated from | `feature-spec` @ SDLC template library `0.2.1` |
15
+
16
+ ## Problem & Goal
17
+
18
+ The prior deterministic conformance pass checked section presence but did not verify that sequence-inventory rows mapped to actual operation-specific diagrams, that migrated diagrams appeared in the canonical section selected by meaning, or that every required section remained concrete after migration. A read-only brownfield audit found cross-module structural and source-fidelity gaps despite clean semantic validation metadata.
19
+
20
+ The goal is to make all nine module specs satisfy the full module-spec output contract while preserving current source behavior and routed legacy detail.
21
+
22
+ ## Scope
23
+
24
+ In scope:
25
+
26
+ - Repair sequence inventories, diagram placement, operation coverage, and error/timeout/retry/recovery branches.
27
+ - Correct Task AQM completion semantics and Utils cache-key scope semantics from current source.
28
+ - Add complete requirement-to-test mappings.
29
+ - Replace generic pitfalls and module conventions with code-grounded module-specific content.
30
+ - Remove stale validation-pending text and superseded local-doc routing artifacts.
31
+ - Normalize mechanically fragmented tables without dropping rows.
32
+ - Reconcile diagram dispositions in source-fidelity inventories and rerun generator-side gates.
33
+
34
+ Out of scope:
35
+
36
+ - Runtime source or test changes.
37
+ - Public API, event, behavior, transport, timeout, or compatibility changes.
38
+ - `.sdd/manifest.json` edits or coverage-status promotion.
39
+ - Independent validator acceptance on the generator runtime.
40
+
41
+ ## Requirements
42
+
43
+ | ID | WHAT | WHY | Acceptance | State |
44
+ |---|---|---|---|---|
45
+ | REMEDIATION-R-001 | Every Sequence Diagram(s) inventory must map each distinct operation group to an actual titled diagram or an explicitly justified shared diagram. | A table that advertises uncovered flows is not actionable documentation. | Coverage rows and diagrams agree; distinct failure/state outcomes are diagrammed. | Approved |
46
+ | REMEDIATION-R-002 | Migrated flow, sequence, class, and state diagrams must appear in the canonical section selected by meaning and remain one-for-one unless code requires a recorded correction. | Source fidelity cannot be satisfied by retaining valid detail only in superseded documents. | Diagram inventory targets/statuses and canonical placement agree. | Approved |
47
+ | REMEDIATION-R-003 | Every module test strategy must map every requirement ID to concrete test files and an explicit remaining gap. | Prose-only testing guidance cannot prove requirement coverage. | Nine complete requirement-to-test matrices. | Approved |
48
+ | REMEDIATION-R-004 | Pitfalls and module conventions must name module-specific failure modes, ownership boundaries, constants, events, or lifecycle constraints. | Generic boilerplate is not evidence-backed maintenance guidance. | No repeated generic ownership/raw-string boilerplate remains. | Approved |
49
+ | REMEDIATION-R-005 | Correct Task AQM and Utils cache-key descriptions to current source behavior. | The existing Task diagram treats HTTP acknowledgement as completion, and Utils overstates `orgId` as the only runtime scope key. | AQM resolves on matched WebSocket completion; cache scope records `orgId` or `bookId` by consumer. | Approved |
50
+ | REMEDIATION-R-006 | Remove stale validation-pending cells and legacy “this file”/superseded-doc navigation from canonical specs. | Canonical docs must describe their current status and route readers to canonical surfaces. | Metadata and requirement gap cells agree; no module-local legacy doc is presented as canonical. | Approved |
51
+ | REMEDIATION-R-007 | Preserve all current table rows while consolidating repeated one-row table fragments. | Mechanical migration fragmentation harms reviewability and can conceal omissions. | Repeated adjacent identical table headers are consolidated without data loss. | Approved |
52
+
53
+ ## MODIFIED Requirements
54
+
55
+ ### MOD-001 — Contact Center
56
+
57
+ Name and map its four lifecycle sequence diagrams, add the bootstrap rejection branch, complete concrete pitfalls/conventions, and retain its full requirement-to-test matrix.
58
+
59
+ ### MOD-002 — Metrics
60
+
61
+ Preserve the two legacy sequences, add explicit disabled/submission-error coverage, complete the test matrix, and normalize event/taxonomy tables.
62
+
63
+ ### MOD-003 — Services
64
+
65
+ Add the missing direct-REST sequence, use the three-column sequence inventory, complete the test matrix, and remove copied legacy-file identity text.
66
+
67
+ ### MOD-004 — Agent
68
+
69
+ Restore code-supported station-login, state-change, WebSocket-event, and relogin detail; add logout/buddy coverage; correct legacy diagram dispositions; and complete the test matrix.
70
+
71
+ ### MOD-005 — Config
72
+
73
+ Keep the corrected ten-result profile aggregation, add pagination coverage, complete the test matrix, and normalize API/type tables.
74
+
75
+ ### MOD-006 — Core
76
+
77
+ Add authenticated REST coverage, diagram duplicate-pending/offline retry behavior, identify private helpers as internal, correct diagram dispositions, and complete the test matrix.
78
+
79
+ ### MOD-007 — Task
80
+
81
+ Move legacy sequences from Data Flow to Sequence Diagram(s), correct AQM completion, add all five operation-group diagrams, and complete the test matrix.
82
+
83
+ ### MOD-008 — Task state machine
84
+
85
+ Add group-specific sequences for offer/assignment, hold/resume, consult, conference/transfer, wrapup/termination, and hydration; preserve exact state diagrams; complete the test matrix.
86
+
87
+ ### MOD-009 — Utils
88
+
89
+ Describe the caller-supplied cache scope accurately, add lookup/store and clear sequences with backend failure behavior, correct legacy diagram disposition, and complete the test matrix.
90
+
91
+ ### MOD-010 — Cross-module audit state
92
+
93
+ Refresh source-fidelity dispositions, conformance evidence, validation metadata/gap wording, local navigation, and decision logs without modifying the manifest.
94
+
95
+ ## Acceptance Criteria
96
+
97
+ - All nine specs pass template/profile/heading/link/placeholder checks.
98
+ - Every sequence inventory maps to actual diagrams with applicable failure/recovery behavior.
99
+ - No sequence diagram remains in Task Data Flow.
100
+ - Task AQM diagrams distinguish HTTP acknowledgement from WebSocket settlement.
101
+ - Utils documents the real consumer scope (`orgId` for EntryPoint/Queue; `bookId` for AddressBook).
102
+ - Every requirement ID appears in its module's test-strategy matrix.
103
+ - No runtime/test file changes and manifest hash remains unchanged.
104
+ - Generator-side source-fidelity and conformance pass before independent validator handoff.
105
+
106
+ ## Change Log
107
+
108
+ | Date | Change | By | Why |
109
+ |---|---|---|---|
110
+ | 2026-07-09 | Created and approved MOD-001 through MOD-010 | Codex + developer | Repair all-module brownfield conformance and source-fidelity gaps found by read-only audit |
111
+ | 2026-07-09 | Applied remediation and completed generator-side gates | Codex | 12/12 fidelity inventories, 9/9 module conformance, and 9/9 coverage pass; manifest unchanged |
112
+
113
+ ## References
114
+
115
+ - Current behavior: `src/` and `test/`
116
+ - Canonical routing: [`SPEC_INDEX.md`](../../../SPEC_INDEX.md)
117
+ - Public contract index: [`CONTRACTS.md`](../../../CONTRACTS.md)