@indexnetwork/protocol 22.0.0-rc.499.1 → 64.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +1841 -0
- package/IMPLEMENTATION.md +140 -181
- package/README.md +16 -20
- package/STABILITY.md +16 -11
- package/dist/{intents/intent.module.d.ts → capabilities/intents.d.ts} +182 -192
- package/dist/capabilities/intents.js +88 -0
- package/dist/capabilities/negotiations.d.ts +17 -0
- package/dist/capabilities/negotiations.js +16 -0
- package/dist/{networks/network.module.d.ts → capabilities/networks.d.ts} +33 -169
- package/dist/{networks/network.module.js → capabilities/networks.js} +6 -17
- package/dist/index.d.ts +57 -134
- package/dist/index.js +41 -105
- package/dist/internal/agents/agent.repository.port.d.ts +59 -0
- package/dist/internal/agents/agent.repository.port.js +7 -0
- package/dist/internal/agents/agent.types.d.ts +35 -0
- package/dist/{agents → internal/agents}/agent.types.js +1 -6
- package/dist/{intents → internal/intents}/graph/intent.graph.d.ts +142 -151
- package/dist/{intents → internal/intents}/graph/intent.graph.execute.d.ts +5 -1
- package/dist/{intents → internal/intents}/graph/intent.graph.execute.js +165 -46
- package/dist/internal/intents/graph/intent.graph.infer.d.ts +78 -0
- package/dist/internal/intents/graph/intent.graph.infer.js +122 -0
- package/dist/internal/intents/graph/intent.graph.js +108 -0
- package/dist/{intents → internal/intents}/graph/intent.graph.reconcile.d.ts +18 -9
- package/dist/internal/intents/graph/intent.graph.reconcile.js +173 -0
- package/dist/internal/intents/graph/intent.graph.shared.d.ts +55 -0
- package/dist/{intents → internal/intents}/graph/intent.graph.shared.js +25 -70
- package/dist/{intents → internal/intents}/graph/intent.graph.state.d.ts +96 -32
- package/dist/{intents → internal/intents}/graph/intent.graph.state.js +42 -31
- package/dist/internal/intents/intent.admission.d.ts +16 -0
- package/dist/internal/intents/intent.admission.js +30 -0
- package/dist/{intents → internal/intents}/intent.inferrer.d.ts +1 -40
- package/dist/{intents → internal/intents}/intent.inferrer.js +13 -49
- package/dist/internal/intents/intent.preparer.d.ts +52 -0
- package/dist/internal/intents/intent.preparer.js +87 -0
- package/dist/{intents → internal/intents}/intent.verifier.d.ts +3 -36
- package/dist/{intents → internal/intents}/intent.verifier.js +0 -17
- package/dist/{networks → internal/networks}/indexer.graph.d.ts +15 -200
- package/dist/{networks → internal/networks}/indexer.graph.js +19 -128
- package/dist/{networks → internal/networks}/indexer.state.d.ts +8 -63
- package/dist/internal/networks/indexer.state.js +70 -0
- package/dist/{networks → internal/networks}/membership.graph.d.ts +6 -6
- package/dist/{networks → internal/networks}/membership.graph.js +3 -3
- package/dist/{networks → internal/networks}/membership.state.d.ts +2 -2
- package/dist/{networks → internal/networks}/membership.state.js +2 -2
- package/dist/{networks → internal/networks}/network.graph.d.ts +9 -22
- package/dist/{networks → internal/networks}/network.graph.js +13 -27
- package/dist/{networks → internal/networks}/network.recommender.d.ts +2 -2
- package/dist/{networks → internal/networks}/network.recommender.js +2 -2
- package/dist/{networks → internal/networks}/network.state.d.ts +4 -7
- package/dist/{networks → internal/networks}/network.state.js +4 -4
- package/dist/internal/opportunities/negotiation-context.loader.d.ts +26 -0
- package/dist/internal/opportunities/negotiation-context.loader.js +36 -0
- package/dist/{opportunities → internal/opportunities}/opportunity.actor.d.ts +1 -1
- package/dist/{opportunities → internal/opportunities}/opportunity.actor.js +7 -1
- package/dist/internal/opportunities/opportunity.counterparties.d.ts +17 -0
- package/dist/internal/opportunities/opportunity.counterparties.js +19 -0
- package/dist/internal/opportunities/opportunity.events.d.ts +38 -0
- package/dist/internal/opportunities/opportunity.events.js +94 -0
- package/dist/{opportunities → internal/opportunities}/opportunity.feed-selection.d.ts +3 -9
- package/dist/internal/opportunities/opportunity.feed-selection.js +40 -0
- package/dist/internal/opportunities/opportunity.graph.modes.d.ts +39 -0
- package/dist/internal/opportunities/opportunity.graph.modes.js +138 -0
- package/dist/{opportunities → internal/opportunities}/opportunity.labels.d.ts +2 -3
- package/dist/internal/opportunities/opportunity.labels.js +9 -0
- package/dist/{opportunities → internal/opportunities}/opportunity.presentation.d.ts +17 -86
- package/dist/{opportunities → internal/opportunities}/opportunity.presentation.js +54 -447
- package/dist/{opportunities → internal/opportunities}/opportunity.update-admission.d.ts +2 -2
- package/dist/internal/opportunities/opportunity.utils.d.ts +105 -0
- package/dist/internal/opportunities/opportunity.utils.js +165 -0
- package/dist/{opportunities → internal/opportunities}/radar/radar.graph.d.ts +17 -17
- package/dist/{opportunities → internal/opportunities}/radar/radar.graph.js +41 -161
- package/dist/{opportunities → internal/opportunities}/radar/radar.state.d.ts +4 -11
- package/dist/{shared → internal/shared}/agent/model-signal.d.ts +1 -1
- package/dist/{shared → internal/shared}/agent/model-signal.js +1 -1
- package/dist/{shared → internal/shared}/agent/model.config.d.ts +28 -86
- package/dist/{shared → internal/shared}/agent/model.config.js +58 -69
- package/dist/internal/shared/agent/model.resolver.d.ts +33 -0
- package/dist/{shared → internal/shared}/agent/model.resolver.js +18 -33
- package/dist/internal/shared/agent/scope.d.ts +20 -0
- package/dist/internal/shared/agent/scope.js +24 -0
- package/dist/internal/shared/assignment/network-assignment.policy.d.ts +23 -0
- package/dist/internal/shared/assignment/network-assignment.policy.js +28 -0
- package/dist/{shared → internal/shared}/observability/log.d.ts +3 -6
- package/dist/{shared → internal/shared}/observability/log.js +9 -18
- package/dist/{shared → internal/shared}/observability/protocol.logger.d.ts +1 -1
- package/dist/{shared → internal/shared}/observability/protocol.logger.js +1 -1
- package/dist/internal/shared/observability/request-context.d.ts +29 -0
- package/dist/internal/shared/observability/request-context.js +17 -0
- package/dist/{shared → internal/shared}/utils/social-label.d.ts +2 -2
- package/dist/{shared → internal/shared}/utils/social-label.js +1 -1
- package/dist/platform/database/capabilities.d.ts +59 -0
- package/dist/{shared/interfaces/database.entities.d.ts → platform/database/entities.d.ts} +81 -121
- package/dist/{shared/interfaces/database.identity-queries.d.ts → platform/database/identity-queries.d.ts} +55 -20
- package/dist/platform/database/member-queries.d.ts +55 -0
- package/dist/platform/database/member-queries.js +4 -0
- package/dist/platform/database/negotiation.d.ts +38 -0
- package/dist/{shared/interfaces/database.network-queries.d.ts → platform/database/network-queries.d.ts} +66 -67
- package/dist/platform/database/network-queries.js +4 -0
- package/dist/{shared/interfaces/database.opportunity-queries.d.ts → platform/database/opportunity-queries.d.ts} +25 -109
- package/dist/{shared/interfaces/database.port.d.ts → platform/database/port.d.ts} +52 -117
- package/dist/{shared/interfaces/database.port.js → platform/database/port.js} +3 -5
- package/dist/platform/database.d.ts +23 -0
- package/dist/{shared/interfaces/database.interface.js → platform/database.js} +1 -1
- package/dist/{shared/interfaces/cache.interface.d.ts → platform/discovery/cache.d.ts} +2 -4
- package/dist/{shared/interfaces/cache.interface.js → platform/discovery/cache.js} +1 -1
- package/dist/platform/discovery/embedder.d.ts +31 -0
- package/dist/platform/runtime/errors.d.ts +6 -0
- package/dist/platform/runtime/errors.js +9 -0
- package/dist/platform/runtime/follow-up.d.ts +36 -0
- package/dist/platform/runtime/follow-up.js +4 -0
- package/dist/platform/runtime/observability.d.ts +34 -0
- package/dist/protocol/core.d.ts +11 -0
- package/dist/protocol/discovery.rules.d.ts +21 -0
- package/dist/protocol/discovery.rules.js +29 -0
- package/dist/protocol/negotiation.constants.d.ts +3 -0
- package/dist/protocol/negotiation.constants.js +3 -0
- package/dist/protocol/negotiation.rules.d.ts +73 -0
- package/dist/protocol/negotiation.rules.js +68 -0
- package/dist/protocol/protocol.prompt.d.ts +13 -0
- package/dist/protocol/protocol.prompt.js +190 -0
- package/dist/{shared → protocol}/schemas/discovery-question.schema.d.ts +13 -13
- package/dist/{shared → protocol}/schemas/discovery-question.schema.js +2 -2
- package/dist/{shared → protocol}/schemas/identity.schema.d.ts +4 -4
- package/dist/{shared → protocol}/schemas/identity.schema.js +4 -4
- package/dist/{shared → protocol}/schemas/network-assignment.schema.d.ts +11 -20
- package/dist/{shared → protocol}/schemas/network-assignment.schema.js +2 -9
- package/dist/protocol/schemas/underspecification.schema.d.ts +9 -0
- package/dist/protocol/schemas/underspecification.schema.js +12 -0
- package/package.json +7 -15
- package/dist/agents/agent.dispatcher.port.d.ts +0 -25
- package/dist/agents/agent.module.d.ts +0 -19
- package/dist/agents/agent.module.js +0 -11
- package/dist/agents/agent.repository.port.d.ts +0 -118
- package/dist/agents/agent.repository.port.js +0 -10
- package/dist/agents/agent.tools.d.ts +0 -16
- package/dist/agents/agent.tools.js +0 -351
- package/dist/agents/agent.tools.port.d.ts +0 -22
- package/dist/agents/agent.tools.port.js +0 -18
- package/dist/agents/agent.types.d.ts +0 -76
- package/dist/chat/chat-streaming.types.d.ts +0 -618
- package/dist/chat/chat-streaming.types.js +0 -297
- package/dist/chat/chat.agent.d.ts +0 -292
- package/dist/chat/chat.agent.js +0 -1010
- package/dist/chat/chat.graph.d.ts +0 -424
- package/dist/chat/chat.graph.js +0 -257
- package/dist/chat/chat.interrupt.classifier.d.ts +0 -25
- package/dist/chat/chat.interrupt.classifier.js +0 -64
- package/dist/chat/chat.persona.d.ts +0 -39
- package/dist/chat/chat.prompt.d.ts +0 -4
- package/dist/chat/chat.prompt.js +0 -12
- package/dist/chat/chat.prompt.modules.d.ts +0 -30
- package/dist/chat/chat.prompt.modules.js +0 -40
- package/dist/chat/chat.question-dedup.d.ts +0 -14
- package/dist/chat/chat.question-dedup.js +0 -17
- package/dist/chat/chat.state.d.ts +0 -135
- package/dist/chat/chat.state.js +0 -120
- package/dist/chat/chat.streamer.d.ts +0 -64
- package/dist/chat/chat.streamer.js +0 -217
- package/dist/chat/chat.suggester.d.ts +0 -23
- package/dist/chat/chat.suggester.js +0 -95
- package/dist/chat/chat.summarizer.d.ts +0 -20
- package/dist/chat/chat.summarizer.js +0 -97
- package/dist/chat/chat.title.generator.d.ts +0 -19
- package/dist/chat/chat.title.generator.js +0 -66
- package/dist/chat/chat.tools.d.ts +0 -5
- package/dist/chat/chat.tools.js +0 -62
- package/dist/chat/chat.utils.d.ts +0 -41
- package/dist/chat/chat.utils.js +0 -88
- package/dist/chat/negotiator.persona.d.ts +0 -74
- package/dist/chat/negotiator.persona.js +0 -154
- package/dist/chat/negotiator.prompt.d.ts +0 -45
- package/dist/chat/negotiator.prompt.js +0 -160
- package/dist/chat/negotiator.tools.d.ts +0 -42
- package/dist/chat/negotiator.tools.js +0 -134
- package/dist/chat/onboarding.persona.d.ts +0 -28
- package/dist/chat/onboarding.persona.js +0 -86
- package/dist/chat/onboarding.prompt.d.ts +0 -6
- package/dist/chat/onboarding.prompt.js +0 -63
- package/dist/chat/signal.persona.d.ts +0 -47
- package/dist/chat/signal.persona.js +0 -319
- package/dist/chat/signal.prompt.d.ts +0 -39
- package/dist/chat/signal.prompt.js +0 -136
- package/dist/contacts/contact.module.d.ts +0 -8
- package/dist/contacts/contact.module.js +0 -6
- package/dist/contacts/contact.repository.port.d.ts +0 -21
- package/dist/contacts/contact.repository.port.js +0 -12
- package/dist/contacts/contact.tools.d.ts +0 -17
- package/dist/contacts/contact.tools.js +0 -108
- package/dist/contacts/contact.tools.port.d.ts +0 -20
- package/dist/contacts/contact.tools.port.js +0 -16
- package/dist/contacts/contact.types.d.ts +0 -24
- package/dist/contacts/contact.types.js +0 -8
- package/dist/contexts/context.generator.d.ts +0 -95
- package/dist/contexts/context.generator.js +0 -127
- package/dist/contexts/context.module.d.ts +0 -13
- package/dist/contexts/context.module.js +0 -12
- package/dist/contexts/context.tools.port.d.ts +0 -9
- package/dist/discovery/hyde.documents.d.ts +0 -9
- package/dist/discovery/hyde.documents.js +0 -49
- package/dist/discovery/hyde.env.d.ts +0 -8
- package/dist/discovery/hyde.env.js +0 -9
- package/dist/discovery/hyde.frame.d.ts +0 -150
- package/dist/discovery/hyde.frame.js +0 -107
- package/dist/discovery/hyde.generator.d.ts +0 -38
- package/dist/discovery/hyde.generator.js +0 -103
- package/dist/discovery/hyde.graph.d.ts +0 -209
- package/dist/discovery/hyde.graph.js +0 -482
- package/dist/discovery/hyde.state.d.ts +0 -70
- package/dist/discovery/hyde.state.js +0 -85
- package/dist/discovery/hyde.strategies.d.ts +0 -17
- package/dist/discovery/hyde.strategies.js +0 -34
- package/dist/discovery/hyde.validator.d.ts +0 -78
- package/dist/discovery/hyde.validator.js +0 -48
- package/dist/discovery/index.d.ts +0 -26
- package/dist/discovery/index.js +0 -19
- package/dist/discovery/lens.inferrer.d.ts +0 -214
- package/dist/discovery/lens.inferrer.js +0 -152
- package/dist/enrichment/enrichment.generator.d.ts +0 -68
- package/dist/enrichment/enrichment.generator.js +0 -95
- package/dist/enrichment/enrichment.graph.d.ts +0 -544
- package/dist/enrichment/enrichment.graph.js +0 -695
- package/dist/enrichment/enrichment.state.d.ts +0 -141
- package/dist/enrichment/enrichment.state.js +0 -115
- package/dist/enrichment/enrichment.tools.context-read.d.ts +0 -10
- package/dist/enrichment/enrichment.tools.context-read.js +0 -353
- package/dist/enrichment/enrichment.tools.context-write.d.ts +0 -9
- package/dist/enrichment/enrichment.tools.context-write.js +0 -417
- package/dist/enrichment/enrichment.tools.d.ts +0 -13
- package/dist/enrichment/enrichment.tools.helpers.d.ts +0 -139
- package/dist/enrichment/enrichment.tools.helpers.js +0 -234
- package/dist/enrichment/enrichment.tools.js +0 -153
- package/dist/intents/graph/intent.graph.infer.d.ts +0 -44
- package/dist/intents/graph/intent.graph.infer.js +0 -97
- package/dist/intents/graph/intent.graph.js +0 -134
- package/dist/intents/graph/intent.graph.reconcile.js +0 -274
- package/dist/intents/graph/intent.graph.shared.d.ts +0 -68
- package/dist/intents/intake/intake.orchestrator.d.ts +0 -203
- package/dist/intents/intake/intake.orchestrator.js +0 -255
- package/dist/intents/intake/intake.pack.generator.d.ts +0 -57
- package/dist/intents/intake/intake.pack.generator.js +0 -90
- package/dist/intents/intent.clarifier.d.ts +0 -51
- package/dist/intents/intent.clarifier.js +0 -201
- package/dist/intents/intent.indexer.d.ts +0 -82
- package/dist/intents/intent.indexer.js +0 -170
- package/dist/intents/intent.module.js +0 -103
- package/dist/intents/intent.proposal.d.ts +0 -37
- package/dist/intents/intent.proposal.js +0 -14
- package/dist/intents/intent.reconciler.d.ts +0 -105
- package/dist/intents/intent.reconciler.js +0 -186
- package/dist/intents/intent.tools.d.ts +0 -27
- package/dist/intents/intent.tools.js +0 -808
- package/dist/maintenance/maintenance.graph.d.ts +0 -239
- package/dist/maintenance/maintenance.graph.js +0 -199
- package/dist/maintenance/maintenance.state.d.ts +0 -35
- package/dist/maintenance/maintenance.state.js +0 -55
- package/dist/mcp/elicitation.builder.d.ts +0 -53
- package/dist/mcp/elicitation.builder.js +0 -74
- package/dist/mcp/elicitation.dispatcher.d.ts +0 -36
- package/dist/mcp/elicitation.dispatcher.js +0 -86
- package/dist/mcp/mcp.authorization-policy.d.ts +0 -252
- package/dist/mcp/mcp.authorization-policy.js +0 -535
- package/dist/mcp/mcp.server.d.ts +0 -90
- package/dist/mcp/mcp.server.js +0 -631
- package/dist/negotiations/insight.generator.d.ts +0 -31
- package/dist/negotiations/insight.generator.js +0 -105
- package/dist/negotiations/negotiation.agent.d.ts +0 -130
- package/dist/negotiations/negotiation.agent.js +0 -396
- package/dist/negotiations/negotiation.answer-consumption.d.ts +0 -223
- package/dist/negotiations/negotiation.answer-consumption.js +0 -275
- package/dist/negotiations/negotiation.attribution.d.ts +0 -91
- package/dist/negotiations/negotiation.attribution.js +0 -109
- package/dist/negotiations/negotiation.candidates.d.ts +0 -83
- package/dist/negotiations/negotiation.candidates.js +0 -162
- package/dist/negotiations/negotiation.client-dm.d.ts +0 -50
- package/dist/negotiations/negotiation.client-dm.js +0 -66
- package/dist/negotiations/negotiation.consultation-policy.d.ts +0 -95
- package/dist/negotiations/negotiation.consultation-policy.js +0 -159
- package/dist/negotiations/negotiation.deadlock.contracts.d.ts +0 -10
- package/dist/negotiations/negotiation.deadlock.d.ts +0 -87
- package/dist/negotiations/negotiation.deadlock.js +0 -150
- package/dist/negotiations/negotiation.detail-reader.d.ts +0 -94
- package/dist/negotiations/negotiation.detail-reader.js +0 -91
- package/dist/negotiations/negotiation.expected-speaker.d.ts +0 -33
- package/dist/negotiations/negotiation.expected-speaker.js +0 -59
- package/dist/negotiations/negotiation.graph.d.ts +0 -694
- package/dist/negotiations/negotiation.graph.finalize.d.ts +0 -5
- package/dist/negotiations/negotiation.graph.finalize.js +0 -403
- package/dist/negotiations/negotiation.graph.init.d.ts +0 -54
- package/dist/negotiations/negotiation.graph.init.js +0 -256
- package/dist/negotiations/negotiation.graph.js +0 -94
- package/dist/negotiations/negotiation.graph.screen.d.ts +0 -23
- package/dist/negotiations/negotiation.graph.screen.js +0 -108
- package/dist/negotiations/negotiation.graph.shared.d.ts +0 -111
- package/dist/negotiations/negotiation.graph.shared.js +0 -168
- package/dist/negotiations/negotiation.graph.turn.d.ts +0 -134
- package/dist/negotiations/negotiation.graph.turn.js +0 -662
- package/dist/negotiations/negotiation.hermes-contract.d.ts +0 -31
- package/dist/negotiations/negotiation.hermes-contract.js +0 -72
- package/dist/negotiations/negotiation.intent-snapshot-provenance.d.ts +0 -21
- package/dist/negotiations/negotiation.intent-snapshot-provenance.js +0 -28
- package/dist/negotiations/negotiation.lifecycle-narration.d.ts +0 -18
- package/dist/negotiations/negotiation.lifecycle-narration.js +0 -87
- package/dist/negotiations/negotiation.memory.d.ts +0 -65
- package/dist/negotiations/negotiation.memory.js +0 -83
- package/dist/negotiations/negotiation.module.d.ts +0 -36
- package/dist/negotiations/negotiation.module.js +0 -23
- package/dist/negotiations/negotiation.protocol.d.ts +0 -1018
- package/dist/negotiations/negotiation.protocol.js +0 -224
- package/dist/negotiations/negotiation.question-safety.d.ts +0 -52
- package/dist/negotiations/negotiation.question-safety.js +0 -119
- package/dist/negotiations/negotiation.reflect.d.ts +0 -194
- package/dist/negotiations/negotiation.reflect.js +0 -145
- package/dist/negotiations/negotiation.scope.d.ts +0 -41
- package/dist/negotiations/negotiation.scope.js +0 -39
- package/dist/negotiations/negotiation.screen.contracts.d.ts +0 -88
- package/dist/negotiations/negotiation.screen.contracts.js +0 -58
- package/dist/negotiations/negotiation.screen.d.ts +0 -78
- package/dist/negotiations/negotiation.screen.js +0 -112
- package/dist/negotiations/negotiation.stall-gap.d.ts +0 -83
- package/dist/negotiations/negotiation.stall-gap.js +0 -152
- package/dist/negotiations/negotiation.stance.contracts.d.ts +0 -123
- package/dist/negotiations/negotiation.stance.contracts.js +0 -317
- package/dist/negotiations/negotiation.state.d.ts +0 -597
- package/dist/negotiations/negotiation.state.js +0 -286
- package/dist/negotiations/negotiation.summarizer.d.ts +0 -25
- package/dist/negotiations/negotiation.summarizer.js +0 -101
- package/dist/negotiations/negotiation.task-lock-policy.d.ts +0 -10
- package/dist/negotiations/negotiation.task-lock-policy.js +0 -22
- package/dist/negotiations/negotiation.tools.d.ts +0 -18
- package/dist/negotiations/negotiation.tools.js +0 -842
- package/dist/negotiations/negotiation.tools.port.d.ts +0 -17
- package/dist/negotiations/negotiation.turn-cap.d.ts +0 -9
- package/dist/negotiations/negotiation.turn-cap.js +0 -12
- package/dist/networks/indexer.state.js +0 -112
- package/dist/networks/network.tools.d.ts +0 -36
- package/dist/networks/network.tools.js +0 -594
- package/dist/opportunities/delivery-card.cache.d.ts +0 -25
- package/dist/opportunities/delivery-card.cache.js +0 -43
- package/dist/opportunities/discovery.env.d.ts +0 -20
- package/dist/opportunities/discovery.env.js +0 -109
- package/dist/opportunities/discriminator/discriminator.adjustments.d.ts +0 -90
- package/dist/opportunities/discriminator/discriminator.adjustments.js +0 -141
- package/dist/opportunities/discriminator/discriminator.assigner.d.ts +0 -78
- package/dist/opportunities/discriminator/discriminator.assigner.js +0 -153
- package/dist/opportunities/discriminator/discriminator.env.d.ts +0 -103
- package/dist/opportunities/discriminator/discriminator.env.js +0 -103
- package/dist/opportunities/discriminator/discriminator.miner.d.ts +0 -114
- package/dist/opportunities/discriminator/discriminator.miner.js +0 -228
- package/dist/opportunities/discriminator/discriminator.push.d.ts +0 -13
- package/dist/opportunities/discriminator/discriminator.push.js +0 -19
- package/dist/opportunities/discriminator/discriminator.question.d.ts +0 -58
- package/dist/opportunities/discriminator/discriminator.question.js +0 -155
- package/dist/opportunities/discriminator/discriminator.scorer.d.ts +0 -32
- package/dist/opportunities/discriminator/discriminator.scorer.js +0 -105
- package/dist/opportunities/discriminator/discriminator.shadow.d.ts +0 -32
- package/dist/opportunities/discriminator/discriminator.shadow.js +0 -90
- package/dist/opportunities/discriminator/discriminator.types.d.ts +0 -93
- package/dist/opportunities/discriminator/discriminator.types.js +0 -18
- package/dist/opportunities/negotiation-context.loader.d.ts +0 -59
- package/dist/opportunities/negotiation-context.loader.js +0 -90
- package/dist/opportunities/negotiation-evidence/negotiation-evidence.env.d.ts +0 -43
- package/dist/opportunities/negotiation-evidence/negotiation-evidence.env.js +0 -44
- package/dist/opportunities/negotiation-evidence/negotiation-evidence.extractor.d.ts +0 -24
- package/dist/opportunities/negotiation-evidence/negotiation-evidence.extractor.js +0 -188
- package/dist/opportunities/negotiation-evidence/negotiation-evidence.miner.d.ts +0 -26
- package/dist/opportunities/negotiation-evidence/negotiation-evidence.miner.js +0 -112
- package/dist/opportunities/negotiation-evidence/negotiation-evidence.shadow.d.ts +0 -19
- package/dist/opportunities/negotiation-evidence/negotiation-evidence.shadow.js +0 -61
- package/dist/opportunities/negotiation-evidence/negotiation-evidence.types.d.ts +0 -191
- package/dist/opportunities/negotiation-evidence/negotiation-evidence.types.js +0 -18
- package/dist/opportunities/negotiation-evidence/negotiation-evidence.verifier.d.ts +0 -34
- package/dist/opportunities/negotiation-evidence/negotiation-evidence.verifier.js +0 -91
- package/dist/opportunities/negotiation-summary.builder.d.ts +0 -37
- package/dist/opportunities/negotiation-summary.builder.js +0 -66
- package/dist/opportunities/opportunity.discovery-negotiation-summary.d.ts +0 -14
- package/dist/opportunities/opportunity.discovery-negotiation-summary.js +0 -46
- package/dist/opportunities/opportunity.enricher.d.ts +0 -71
- package/dist/opportunities/opportunity.enricher.js +0 -280
- package/dist/opportunities/opportunity.evaluator.d.ts +0 -289
- package/dist/opportunities/opportunity.evaluator.js +0 -516
- package/dist/opportunities/opportunity.evidence.d.ts +0 -22
- package/dist/opportunities/opportunity.evidence.js +0 -87
- package/dist/opportunities/opportunity.existing-negotiation.d.ts +0 -79
- package/dist/opportunities/opportunity.existing-negotiation.js +0 -118
- package/dist/opportunities/opportunity.feed-selection.js +0 -96
- package/dist/opportunities/opportunity.graph.d.ts +0 -1611
- package/dist/opportunities/opportunity.graph.discovery-strategies.d.ts +0 -109
- package/dist/opportunities/opportunity.graph.discovery-strategies.js +0 -451
- package/dist/opportunities/opportunity.graph.discovery.d.ts +0 -69
- package/dist/opportunities/opportunity.graph.discovery.js +0 -397
- package/dist/opportunities/opportunity.graph.evaluation.d.ts +0 -82
- package/dist/opportunities/opportunity.graph.evaluation.js +0 -608
- package/dist/opportunities/opportunity.graph.js +0 -193
- package/dist/opportunities/opportunity.graph.modes.d.ts +0 -538
- package/dist/opportunities/opportunity.graph.modes.js +0 -538
- package/dist/opportunities/opportunity.graph.negotiate.d.ts +0 -109
- package/dist/opportunities/opportunity.graph.negotiate.js +0 -392
- package/dist/opportunities/opportunity.graph.persist-node.d.ts +0 -93
- package/dist/opportunities/opportunity.graph.persist-node.js +0 -765
- package/dist/opportunities/opportunity.graph.prep.d.ts +0 -150
- package/dist/opportunities/opportunity.graph.prep.js +0 -381
- package/dist/opportunities/opportunity.graph.shared.d.ts +0 -173
- package/dist/opportunities/opportunity.graph.shared.js +0 -199
- package/dist/opportunities/opportunity.introducer-feature.d.ts +0 -2
- package/dist/opportunities/opportunity.introducer-feature.js +0 -4
- package/dist/opportunities/opportunity.introducer.d.ts +0 -77
- package/dist/opportunities/opportunity.introducer.js +0 -99
- package/dist/opportunities/opportunity.labels.js +0 -10
- package/dist/opportunities/opportunity.lifecycle.d.ts +0 -63
- package/dist/opportunities/opportunity.lifecycle.js +0 -181
- package/dist/opportunities/opportunity.module.d.ts +0 -54
- package/dist/opportunities/opportunity.module.js +0 -39
- package/dist/opportunities/opportunity.newborn-stamping.d.ts +0 -41
- package/dist/opportunities/opportunity.newborn-stamping.js +0 -81
- package/dist/opportunities/opportunity.owner-approval.d.ts +0 -118
- package/dist/opportunities/opportunity.owner-approval.js +0 -34
- package/dist/opportunities/opportunity.owner-provenance.d.ts +0 -6
- package/dist/opportunities/opportunity.owner-provenance.js +0 -28
- package/dist/opportunities/opportunity.persist.d.ts +0 -58
- package/dist/opportunities/opportunity.persist.js +0 -145
- package/dist/opportunities/opportunity.persistence-admission.d.ts +0 -39
- package/dist/opportunities/opportunity.persistence-admission.js +0 -59
- package/dist/opportunities/opportunity.state.d.ts +0 -451
- package/dist/opportunities/opportunity.state.js +0 -256
- package/dist/opportunities/opportunity.tools.cards.d.ts +0 -138
- package/dist/opportunities/opportunity.tools.cards.js +0 -212
- package/dist/opportunities/opportunity.tools.d.ts +0 -12
- package/dist/opportunities/opportunity.tools.js +0 -236
- package/dist/opportunities/opportunity.tools.list.d.ts +0 -10
- package/dist/opportunities/opportunity.tools.list.js +0 -489
- package/dist/opportunities/opportunity.tools.port.d.ts +0 -16
- package/dist/opportunities/opportunity.utils.d.ts +0 -217
- package/dist/opportunities/opportunity.utils.js +0 -395
- package/dist/opportunities/outcome/outcome.env.d.ts +0 -60
- package/dist/opportunities/outcome/outcome.env.js +0 -63
- package/dist/opportunities/outcome/outcome.hypotheses.d.ts +0 -29
- package/dist/opportunities/outcome/outcome.hypotheses.js +0 -117
- package/dist/opportunities/outcome/outcome.shadow.d.ts +0 -56
- package/dist/opportunities/outcome/outcome.shadow.js +0 -87
- package/dist/opportunities/outcome/outcome.types.d.ts +0 -110
- package/dist/opportunities/outcome/outcome.types.js +0 -26
- package/dist/opportunities/radar/radar.health.d.ts +0 -31
- package/dist/opportunities/radar/radar.health.js +0 -75
- package/dist/premises/premise.analyzer.d.ts +0 -35
- package/dist/premises/premise.analyzer.js +0 -115
- package/dist/premises/premise.decomposer.d.ts +0 -69
- package/dist/premises/premise.decomposer.js +0 -213
- package/dist/premises/premise.graph.d.ts +0 -345
- package/dist/premises/premise.graph.js +0 -278
- package/dist/premises/premise.indexer.d.ts +0 -35
- package/dist/premises/premise.indexer.js +0 -86
- package/dist/premises/premise.state.d.ts +0 -67
- package/dist/premises/premise.state.js +0 -94
- package/dist/premises/premise.tools.d.ts +0 -3
- package/dist/premises/premise.tools.js +0 -248
- package/dist/questions/question.env.d.ts +0 -27
- package/dist/questions/question.env.js +0 -27
- package/dist/questions/question.input.d.ts +0 -107
- package/dist/questions/question.module.d.ts +0 -30
- package/dist/questions/question.module.js +0 -28
- package/dist/questions/question.schema.d.ts +0 -1529
- package/dist/questions/question.schema.js +0 -420
- package/dist/shared/agent/activity-projection.d.ts +0 -271
- package/dist/shared/agent/activity-projection.js +0 -254
- package/dist/shared/agent/canonical-guidance.d.ts +0 -30
- package/dist/shared/agent/canonical-guidance.js +0 -246
- package/dist/shared/agent/model.resolver.d.ts +0 -48
- package/dist/shared/agent/tool.factory.d.ts +0 -17
- package/dist/shared/agent/tool.factory.js +0 -221
- package/dist/shared/agent/tool.helpers.d.ts +0 -482
- package/dist/shared/agent/tool.helpers.js +0 -232
- package/dist/shared/agent/tool.registry.d.ts +0 -25
- package/dist/shared/agent/tool.registry.js +0 -76
- package/dist/shared/agent/tool.runtime.d.ts +0 -28
- package/dist/shared/agent/tool.runtime.js +0 -194
- package/dist/shared/agent/tool.scope.d.ts +0 -44
- package/dist/shared/agent/tool.scope.js +0 -50
- package/dist/shared/agent/utility.tools.d.ts +0 -15
- package/dist/shared/agent/utility.tools.js +0 -322
- package/dist/shared/assignment/network-assignment.policy.d.ts +0 -61
- package/dist/shared/assignment/network-assignment.policy.js +0 -105
- package/dist/shared/interfaces/agent-dispatcher.interface.d.ts +0 -100
- package/dist/shared/interfaces/agent-dispatcher.interface.js +0 -12
- package/dist/shared/interfaces/auth.interface.d.ts +0 -37
- package/dist/shared/interfaces/auth.interface.js +0 -1
- package/dist/shared/interfaces/chat-message-writer.interface.d.ts +0 -18
- package/dist/shared/interfaces/chat-message-writer.interface.js +0 -1
- package/dist/shared/interfaces/chat-session.interface.d.ts +0 -23
- package/dist/shared/interfaces/chat-session.interface.js +0 -18
- package/dist/shared/interfaces/chat-summary.interface.d.ts +0 -16
- package/dist/shared/interfaces/chat-summary.interface.js +0 -1
- package/dist/shared/interfaces/database.capabilities.d.ts +0 -100
- package/dist/shared/interfaces/database.interface.d.ts +0 -16
- package/dist/shared/interfaces/database.member-queries.d.ts +0 -219
- package/dist/shared/interfaces/database.member-queries.js +0 -4
- package/dist/shared/interfaces/database.negotiation.d.ts +0 -329
- package/dist/shared/interfaces/database.negotiation.js +0 -26
- package/dist/shared/interfaces/database.network-queries.js +0 -4
- package/dist/shared/interfaces/database.opportunity-queries.js +0 -4
- package/dist/shared/interfaces/delivery-ledger.interface.d.ts +0 -40
- package/dist/shared/interfaces/delivery-ledger.interface.js +0 -5
- package/dist/shared/interfaces/embedder.interface.d.ts +0 -92
- package/dist/shared/interfaces/embedder.interface.js +0 -4
- package/dist/shared/interfaces/enrichment-run.interface.d.ts +0 -62
- package/dist/shared/interfaces/enrichment-run.interface.js +0 -1
- package/dist/shared/interfaces/enrichment.interface.js +0 -1
- package/dist/shared/interfaces/negotiation-events.interface.d.ts +0 -77
- package/dist/shared/interfaces/negotiation-events.interface.js +0 -6
- package/dist/shared/interfaces/negotiation-summary.interface.d.ts +0 -25
- package/dist/shared/interfaces/negotiation-summary.interface.js +0 -1
- package/dist/shared/interfaces/negotiator-memory.interface.d.ts +0 -58
- package/dist/shared/interfaces/negotiator-memory.interface.js +0 -11
- package/dist/shared/interfaces/queue.interface.d.ts +0 -23
- package/dist/shared/interfaces/queue.interface.js +0 -4
- package/dist/shared/interfaces/scraper.interface.js +0 -1
- package/dist/shared/interfaces/tool-request-context.interface.d.ts +0 -11
- package/dist/shared/interfaces/tool-request-context.interface.js +0 -1
- package/dist/shared/observability/request-context.d.ts +0 -27
- package/dist/shared/observability/request-context.js +0 -6
- package/dist/shared/schemas/mcp-auth.schema.d.ts +0 -87
- package/dist/shared/schemas/mcp-auth.schema.js +0 -56
- package/dist/shared/schemas/negotiation-digest.schema.d.ts +0 -58
- package/dist/shared/schemas/negotiation-digest.schema.js +0 -38
- package/dist/shared/schemas/negotiation-state.schema.d.ts +0 -343
- package/dist/shared/schemas/negotiation-state.schema.js +0 -81
- package/dist/shared/schemas/question-block.fixture.d.ts +0 -12
- package/dist/shared/schemas/question-block.fixture.js +0 -39
- package/dist/shared/schemas/question-block.schema.d.ts +0 -111
- package/dist/shared/schemas/question-block.schema.js +0 -124
- package/dist/shared/schemas/structured-question.schema.d.ts +0 -66
- package/dist/shared/schemas/structured-question.schema.js +0 -31
- package/dist/shared/schemas/underspecification.schema.d.ts +0 -13
- package/dist/shared/schemas/underspecification.schema.js +0 -16
- /package/dist/{opportunities → internal/opportunities}/opportunity.update-admission.js +0 -0
- /package/dist/{opportunities → internal/opportunities}/radar/radar.state.js +0 -0
- /package/dist/{shared → internal/shared}/network/metadata.renderer.d.ts +0 -0
- /package/dist/{shared → internal/shared}/network/metadata.renderer.js +0 -0
- /package/dist/{shared → internal/shared}/observability/debug-meta.sanitizer.d.ts +0 -0
- /package/dist/{shared → internal/shared}/observability/debug-meta.sanitizer.js +0 -0
- /package/dist/{shared → internal/shared}/observability/performance.d.ts +0 -0
- /package/dist/{shared → internal/shared}/observability/performance.js +0 -0
- /package/dist/{shared → internal/shared}/observability/trace.d.ts +0 -0
- /package/dist/{shared → internal/shared}/observability/trace.js +0 -0
- /package/dist/{shared → internal/shared}/utils/claim-safety.d.ts +0 -0
- /package/dist/{shared → internal/shared}/utils/claim-safety.js +0 -0
- /package/dist/{shared → internal/shared}/utils/telegram-handle.d.ts +0 -0
- /package/dist/{shared → internal/shared}/utils/telegram-handle.js +0 -0
- /package/dist/{shared/interfaces/database.capabilities.js → platform/database/capabilities.js} +0 -0
- /package/dist/{shared/interfaces/database.entities.js → platform/database/entities.js} +0 -0
- /package/dist/{shared/interfaces/database.identity-queries.js → platform/database/identity-queries.js} +0 -0
- /package/dist/{agents/agent.dispatcher.port.js → platform/database/negotiation.js} +0 -0
- /package/dist/{chat/chat.persona.js → platform/database/opportunity-queries.js} +0 -0
- /package/dist/{contexts/context.tools.port.js → platform/discovery/embedder.js} +0 -0
- /package/dist/{shared/interfaces/scraper.interface.d.ts → platform/discovery/scraper.d.ts} +0 -0
- /package/dist/{negotiations/negotiation.deadlock.contracts.js → platform/discovery/scraper.js} +0 -0
- /package/dist/{shared/interfaces/enrichment.interface.d.ts → platform/enrichment/ports.d.ts} +0 -0
- /package/dist/{negotiations/negotiation.tools.port.js → platform/enrichment/ports.js} +0 -0
- /package/dist/{opportunities/opportunity.tools.port.js → platform/runtime/observability.js} +0 -0
- /package/dist/{questions/question.input.js → protocol/core.js} +0 -0
- /package/dist/{shared → protocol}/schemas/chat-context.schema.d.ts +0 -0
- /package/dist/{shared → protocol}/schemas/chat-context.schema.js +0 -0
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,100 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## 64.0.0
|
|
4
|
+
|
|
5
|
+
### Breaking changes
|
|
6
|
+
|
|
7
|
+
- Opportunity status is a projection of an append-only event log (`opened`, `agreed`, `committed`, `declined`, `expired`). Remove `updateOpportunityStatus` and `deleteOpportunity` exports, `stampOpportunityActorAction`, and `acceptSiblingOpportunities`. Drop `accepted_by` and `actors.actedAt`. One person's commit no longer accepts the row or opens a conversation.
|
|
8
|
+
|
|
9
|
+
## 63.0.0
|
|
10
|
+
|
|
11
|
+
### Breaking changes
|
|
12
|
+
|
|
13
|
+
- **`Intents.clarify()` → `Intents.prepare()`.** Fold recovery answers into the draft, run creation admission, and return `ready` with metadata or `needs_revision` with admission feedback plus a dynamic recovery form. Remove `ClarifyAnswer`, `ClarifyInput`, `ClarifyQuestion`, `ClarifyQuestionOption`, `ClarifyResult`, and `needs_clarification`.
|
|
14
|
+
- Export `PrepareAnswer`, `PrepareInput`, `PrepareResult`, `RecoveryField`, `RecoveryFieldKind`, and `RecoveryFieldOption` instead.
|
|
15
|
+
|
|
16
|
+
## 62.0.0
|
|
17
|
+
|
|
18
|
+
### Breaking changes
|
|
19
|
+
|
|
20
|
+
- Remove outcome-feedback capture and mining from the protocol. Remove the `OutcomeOutbox` export and the optional outbox arguments from the database ports `updateOpportunityStatus` and `stampOpportunityActorAction`; hosts must stop supplying these arguments and remove their feedback capture/mining wiring.
|
|
21
|
+
- Remove `PoolDiscriminatorMiner`, `DiscriminatorMiningInput`, `MinedDiscriminator`, `PoolCandidate`, `isOutcomeQuestionsActivated`, `OUTCOME_MAX_CANDIDATES`, `OUTCOME_MAX_PUBLIC_CONTEXT_CHARS`, `OUTCOME_MIN_INDEPENDENT_EXAMPLES`, `runOutcomeShadow`, `OutcomeExample`, `OutcomeLabel`, and `OutcomeShadowResult` from the public entry point. Delete the internal outcome pipeline and its discriminator miner, types, and evidence-verification helpers without compatibility exports.
|
|
22
|
+
- Remove the `poolDiscriminatorMiner`, `poolDiscriminatorAssigner`, and `negotiationEvidenceMiner` model keys. They are no longer accepted by `getModelName` or `EVAL_MODEL_OVERRIDES`.
|
|
23
|
+
|
|
24
|
+
### Preserved behavior
|
|
25
|
+
|
|
26
|
+
- Negotiation outcomes and presentation, opportunity lifecycle and shared claim-safety guards, and intent preparation, clarification, and scoring are unchanged.
|
|
27
|
+
|
|
28
|
+
## 61.0.0
|
|
29
|
+
|
|
30
|
+
### Breaking changes
|
|
31
|
+
|
|
32
|
+
- A standing proposal cannot be proposed over. `decideNegotiationTurn` rejects a `propose` whose previous turn is the other seat's `propose` as the new `propose_over_offer` rejection, and `observeNegotiation` offers `counter`, `accept`, `decline` to a seat facing a proposal. `propose` keeps its two uses: opening a negotiation, and answering a counter.
|
|
33
|
+
- `NEGOTIATION_GUIDANCE` states the rule alongside the accept rule from 60.0.0.
|
|
34
|
+
|
|
35
|
+
### Why
|
|
36
|
+
|
|
37
|
+
60.0.0 made `propose` legal at every turn index so an answer to a counter could be re-offered. With nothing stopping a proposal from answering a proposal, two agents that already agreed volleyed restatements until the turn limit: one live negotiation ran `propose > counter > propose` ten times and never settled, each turn saying what the other had just said.
|
|
38
|
+
|
|
39
|
+
### Preserved behavior
|
|
40
|
+
|
|
41
|
+
- Settled negotiations, turn limits, seat and eligibility checks, race detection, outcomes and their opportunity statuses are unchanged. No stored enum value changed, so no migration is required. A negotiation mid-flight facing a proposal simply loses `propose` from its menu.
|
|
42
|
+
|
|
43
|
+
## 60.0.0
|
|
44
|
+
|
|
45
|
+
### Breaking changes
|
|
46
|
+
|
|
47
|
+
- A counter is no longer a standing offer. `decideNegotiationTurn` accepts an `accept` only against the other seat's `propose`; an accept whose previous turn is a counter is rejected as `accept_without_offer`. The seat that asked a question is now the one that settles, because answering means proposing again.
|
|
48
|
+
- `propose` is valid at any turn index, not only the opening one. It is how an answer to a counter is put back on the table. The `propose_not_first` rejection is removed from `NegotiationRejection`; `counter_is_first` still blocks a counter at turn 0, and the opening remains a propose or a decline.
|
|
49
|
+
- `observeNegotiation` derives its menu from the same fact. A seat facing a `propose` sees `propose`, `counter`, `accept`, `decline`; a seat facing a `counter` sees `propose`, `counter`, `decline`; an empty log still sees `propose`, `decline`.
|
|
50
|
+
- `NEGOTIATION_GUIDANCE` states the new rule in place of "counter responds with revised terms".
|
|
51
|
+
|
|
52
|
+
### Preserved behavior
|
|
53
|
+
|
|
54
|
+
- Settled negotiations, turn limits, seat and eligibility checks, race detection, and the `agreed`/`declined` outcomes and their opportunity statuses are unchanged. No stored enum value changed, so no migration is required. A negotiation mid-flight whose last turn is a counter simply loses `accept` from its menu.
|
|
55
|
+
|
|
56
|
+
## 59.0.1
|
|
57
|
+
|
|
58
|
+
### Documentation
|
|
59
|
+
|
|
60
|
+
- `IMPLEMENTATION.md` now describes the host's negotiation routes as they are: `GET /api/negotiations` lists a seat's negotiations, and one is observed and turned through its opportunity at `GET /api/opportunities/:id/negotiation` and `POST /api/opportunities/:id/negotiation/turns`. No exported surface changed.
|
|
61
|
+
|
|
62
|
+
## 59.0.0
|
|
63
|
+
|
|
64
|
+
### Breaking changes
|
|
65
|
+
|
|
66
|
+
- Discovery is no longer a post-persist workflow. `IntentFollowUp.onIntentSaved`, `onIntentArchived`, and `onIntentResumed` no longer imply matching work and may do nothing; hosts search on demand instead. The interface shape is unchanged, so implementations keep compiling. `scoreIntent` is unaffected.
|
|
67
|
+
- Remove the `@indexnetwork/discovery` workspace. There is no lens inference, hypothetical-document generation or validation, artifact cache, or match explainer anywhere in the repository. Retrieval is one embedding of the caller's own query against real intent embeddings, and the judging is the caller's.
|
|
68
|
+
|
|
69
|
+
### Preserved behavior
|
|
70
|
+
|
|
71
|
+
- Pair identity and opening are unchanged: `pairKeyOf` plus `openCounterparties(pairs, decideNegotiationOpening)` still writes the opportunity and its negotiation atomically, and remains the only way one is created. Network/broadcast scope (`resolveDiscoveryNetworkScope`, `renderDiscoveryNetworkContext`), negotiation rules, and opportunity lifecycle/presentation are untouched.
|
|
72
|
+
|
|
73
|
+
## 58.0.0
|
|
74
|
+
|
|
75
|
+
### Breaking changes
|
|
76
|
+
|
|
77
|
+
- Extract post-intent discovery into the independent `@indexnetwork/discovery` workspace. Remove `OpportunityGraphFactory`, `OpportunityGraphThresholdOverrides`, `HydeGraphFactory`, `HydeGenerator`, `LensInferrer`, `HydeGraphDatabase`, `HydeCache`, the lens/search DTOs, `buildCandidateEvidence`, and discovery threshold exports from protocol. The extracted path uses plain async TypeScript and validated fetch-based model responses.
|
|
78
|
+
- Replace `IntentFollowUp.generateHyde`, `deleteHyde`, and `resumeDiscovery` with `onIntentSaved`, `onIntentArchived`, and `onIntentResumed`. Scheduling and failure/compensation behavior are unchanged; `scoreIntent` remains a separate best-effort metadata hook.
|
|
79
|
+
- Remove artifact storage methods from protocol database ports and multi-lens retrieval from `Embedder`. Replace `OpportunityGraphDatabase` with the lifecycle/read-only `OpportunityDatabase` port; expose `readOpportunities`, `updateOpportunityStatus`, and `deleteOpportunity` directly. Remove discovery agents from protocol model assignments.
|
|
80
|
+
- Hosts run discovery and commit returned potential pairs with `pairKeyOf` and `decideNegotiationOpening` through atomic `openCounterparties`. Protocol retains intent lifecycle, network/broadcast scope rules, negotiations, and opportunity lifecycle/presentation. Expose `resolveDiscoveryNetworkScope` and `renderDiscoveryNetworkContext` for host composition.
|
|
81
|
+
|
|
82
|
+
### Preserved behavior
|
|
83
|
+
|
|
84
|
+
- Keep source-grounded frame-v1 cache identity and generation cohorts, validation failure semantics, real-intent candidate retrieval, membership checks, per-lens/per-network budgets, rejection cooldown, ranking limits, explanations, and atomic pair uniqueness. Hypothetical documents remain query-side retrieval artifacts.
|
|
85
|
+
|
|
86
|
+
## 57.0.0
|
|
87
|
+
|
|
88
|
+
### Breaking changes
|
|
89
|
+
- `Intents.clarify()` now applies creation admission to the complete draft and returns `ready` with semantic metadata or `needs_clarification` with feedback and questions. Model failures throw for retry; an empty question list no longer substitutes for admission.
|
|
90
|
+
- Explicit graph creation prepares once and persists exactly one new intent verbatim, including when similar intents exist. It no longer infers, rewrites, or reconciles creation into updates or archival. The reconciler agent injection is removed.
|
|
91
|
+
- Hosts may pass authenticated `preparation` to the creation graph to authorize final user revisions without another admission gate. Preserve metadata only when it measures the submitted text; use null metadata after revisions. Never accept preparation objects from untrusted clients.
|
|
92
|
+
- `IntentFollowUp.scoreIntent` is required for best-effort rescoring after edited creation. It must never reject, rewrite, archive, or undo the saved intent and must apply metadata only while the owner and text still match. `Intents.scoreIntent()` returns measurements without admission filters.
|
|
93
|
+
- Export `PreparedIntent` and `IntentSemanticMetadata` for host integration. Existing explicit update, read, archive, and status operations retain their behavior.
|
|
94
|
+
|
|
95
|
+
### Fixed
|
|
96
|
+
- Restrict the generic-job shortcut to bare requests. Qualified searches containing "a job" use the verifier's existing admission thresholds and specificity verdict.
|
|
97
|
+
|
|
3
98
|
All notable changes to `@indexnetwork/protocol` are documented here.
|
|
4
99
|
|
|
5
100
|
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
|
|
@@ -10,6 +105,69 @@ See [STABILITY.md](./STABILITY.md) for the public-contract and tier definitions.
|
|
|
10
105
|
> itemized. From `2.0.0` onward, keep this file updated as part of every release
|
|
11
106
|
> (bump `package.json` and the `[Unreleased]` section before promoting to `main`).
|
|
12
107
|
|
|
108
|
+
|
|
109
|
+
## 56.0.0
|
|
110
|
+
|
|
111
|
+
### Breaking changes
|
|
112
|
+
|
|
113
|
+
- **The tool layer is gone.** `createToolRegistry`, `invokeToolRuntime`,
|
|
114
|
+
`toolRuntimeErrorToResult`, `getToolTimeoutPolicy`, `resolveChatContext`,
|
|
115
|
+
`createEnrichmentTools`, `createOpportunityTools`, `Intents.createTools`,
|
|
116
|
+
`Networks.createTools`, and the `ResolvedToolContext` / `ToolDeps` /
|
|
117
|
+
`RawToolDefinition` / `EnrichmentToolDeps` / `OpportunityToolDeps` /
|
|
118
|
+
`IntentToolDeps` / `NetworkToolDeps` types are removed, along with every
|
|
119
|
+
`*.tools.ts` factory, `tool.registry.ts`, `tool.runtime.ts`, and
|
|
120
|
+
`tool.helpers.ts`. Hosts expose capabilities as their own REST resources and
|
|
121
|
+
reach the protocol through the graph factories and capability classes, which
|
|
122
|
+
are unchanged. `@indexnetwork/agent`'s own `Tool` loop is a different thing
|
|
123
|
+
and is untouched.
|
|
124
|
+
- **`ToolScopeType` is `ScopeType`** and `deriveAllowedNetworkIds` /
|
|
125
|
+
`deriveDiscoveryNetworkIds` moved to `internal/shared/agent/scope.ts`.
|
|
126
|
+
- **`CompositeToolDatabase` is `CompositeDatabase`.** Same members.
|
|
127
|
+
|
|
128
|
+
### Changed
|
|
129
|
+
|
|
130
|
+
- Canonical guidance (`GET /api/docs` in the reference host) describes REST
|
|
131
|
+
resources and CLI commands instead of tool names, and the user event stream is
|
|
132
|
+
documented as `GET /api/events`.
|
|
133
|
+
|
|
134
|
+
## 55.0.0
|
|
135
|
+
|
|
136
|
+
### Breaking changes
|
|
137
|
+
|
|
138
|
+
- Remove MCP serving and authentication exports: `createMcpServer`, `ScopedDepsFactory`, `McpAuthResolver`, `McpAuthInput`, `McpResolvedIdentity`, `buildMcpOnboardingMessage`, and `ONBOARDING_ALLOWED`.
|
|
139
|
+
- Remove `createOpportunityVerdictTools`, the registry `surface` option, and MCP-only tool context/dependency fields. Hosts compose scoped tools through `createToolRegistry` and `invokeToolRuntime`; owner approval remains a separate explicit HTTP operation.
|
|
140
|
+
- External agents use the HTTP API through CLI 0.24.0. `read_docs` now serves canonical HTTP/CLI workflows, and utility tools use one shared registry. Shared execution limits, cancellation, ownership, and network scoping remain in place.
|
|
141
|
+
- Remove the direct MCP SDK dependency. The API host removes `/mcp` and MCP OAuth discovery and drops only the three obsolete OAuth tables.
|
|
142
|
+
|
|
143
|
+
## 54.0.1 - 2026-09-09
|
|
144
|
+
|
|
145
|
+
### Changed
|
|
146
|
+
|
|
147
|
+
- Centralize shared negotiation guidance, MCP instructions, and `read_docs`
|
|
148
|
+
content and composition in `src/protocol/protocol.prompt.ts`. Emitted text,
|
|
149
|
+
topic matching, response envelopes, and package-root exports are unchanged.
|
|
150
|
+
- Share negotiation limits between guidance and enforcement through
|
|
151
|
+
`src/protocol/negotiation.constants.ts`, and document prompt consumers in the
|
|
152
|
+
implementation guide.
|
|
153
|
+
|
|
154
|
+
## 54.0.0
|
|
155
|
+
|
|
156
|
+
### Breaking changes
|
|
157
|
+
|
|
158
|
+
- Add the `Negotiations` participation capability, current-state observations,
|
|
159
|
+
protocol guidance, and atomic host commit contract. Submissions carry the
|
|
160
|
+
observed `expectedTurnCount`; stale decisions are refused.
|
|
161
|
+
- `openCounterparties` now receives a protocol decision callback that hosts must
|
|
162
|
+
evaluate against current network membership and active intent assignments.
|
|
163
|
+
- Replace `NEGOTIATION_MAX_TURNS_AMBIENT` (and the private chat limit) with one
|
|
164
|
+
`NEGOTIATION_MAX_TURNS` of 12. Exhaustion blocks further turns with no outcome;
|
|
165
|
+
A2A agreement advances only to pending human approval.
|
|
166
|
+
- The API host renames domain tables with `protocol_` prefixes, adds private
|
|
167
|
+
`agent_sessions`, and composes the independent agent library through its local
|
|
168
|
+
TUI runner. Forward migrations preserve existing records.
|
|
169
|
+
|
|
170
|
+
|
|
13
171
|
## Release model
|
|
14
172
|
|
|
15
173
|
Every push to `dev` publishes `<package.json version>-rc.<run>.<attempt>` under
|
|
@@ -20,6 +178,1646 @@ went 6.7.1 → 8.0.2 with no 7.x in between because the whole 7.x line shipped a
|
|
|
20
178
|
prereleases between the two promotions. To track every change, read `rc`; to
|
|
21
179
|
pin a supported release, use `latest`.
|
|
22
180
|
|
|
181
|
+
## 53.0.0 - 2026-09-06
|
|
182
|
+
|
|
183
|
+
### Removed
|
|
184
|
+
|
|
185
|
+
- **BREAKING — `mcpRateLimiter` is gone.** Hosts used to inject a per-principal
|
|
186
|
+
throttle on MCP tool dispatch. That hook is deleted; a tool call runs as soon
|
|
187
|
+
as identity resolves.
|
|
188
|
+
|
|
189
|
+
## 52.0.0 - 2026-09-06
|
|
190
|
+
|
|
191
|
+
### Removed
|
|
192
|
+
|
|
193
|
+
- **BREAKING — the MCP capability policy is gone.** `mcp.authorization-policy.ts`
|
|
194
|
+
is deleted along with the `CANONICAL_MCP_CAPABILITY_POLICY_OPTIONS`,
|
|
195
|
+
`McpCapabilityPolicyOptions`, `McpAuthorizationObserver` and
|
|
196
|
+
`McpAuthorizationDenialEvent` exports. `createMcpServer` now takes three
|
|
197
|
+
arguments — `(deps, authResolver, scopedDepsFactory)` — and every
|
|
198
|
+
authenticated caller sees and can call every registered tool. A credential
|
|
199
|
+
names a user, so ownership and membership checks in the handlers are the only
|
|
200
|
+
remaining gate.
|
|
201
|
+
- **BREAKING — agent CRUD is not an MCP tool.** `register_agent`, `list_agents`,
|
|
202
|
+
`update_agent` and `delete_agent` are deleted. Agents are created, updated and
|
|
203
|
+
deleted from the owner's own signed-in session over the host's REST surface.
|
|
204
|
+
`read_own_agent` stays, unchanged, as a plain authenticated tool.
|
|
205
|
+
- The owner-session gate inside `accept_opportunity` and `reject_opportunity` is
|
|
206
|
+
removed. A verdict passed through a key is the owner passing it, and the write
|
|
207
|
+
was always scoped to `context.userId`.
|
|
208
|
+
|
|
209
|
+
## 51.0.0 - 2026-09-06
|
|
210
|
+
|
|
211
|
+
### Removed
|
|
212
|
+
|
|
213
|
+
- **BREAKING — an API key names a user, never an agent.**
|
|
214
|
+
`McpResolvedIdentity` is `{ userId }` plus the session flag: `agentId`,
|
|
215
|
+
`enrollmentCapable`, `isHermesAgent` and `networkScopeId` are gone, along with
|
|
216
|
+
`McpApiKeyMetadataSchema`. Nothing derives a principal from key metadata, so
|
|
217
|
+
the `enrollment_key`, `unregistered_key`, `registered_network_agent` and
|
|
218
|
+
`registered_global_agent` capability profiles are gone too — a caller is
|
|
219
|
+
either a session or a key, and a key gets the full product tool set.
|
|
220
|
+
- **BREAKING — `agent_permissions` is deleted.** `AgentPermissionRecord`,
|
|
221
|
+
`AgentWithRelations` and `GrantPermissionInput` are removed from the public
|
|
222
|
+
types; `AgentDatabase` loses `getAgentWithRelations`, `grantPermission`,
|
|
223
|
+
`revokePermission` and `hasPermission`, and gains `getSelectedNegotiator`.
|
|
224
|
+
The `grant_agent_permission` and `revoke_agent_permission` MCP tools are
|
|
225
|
+
gone, `register_agent` no longer takes `permissions`, and `read_own_agent`
|
|
226
|
+
returns the owner's selected negotiator.
|
|
227
|
+
- **BREAKING — tool access rules collapse to four kinds.**
|
|
228
|
+
`McpToolAccessRule` is `authenticated`, `human_only`, `agent_admin` or
|
|
229
|
+
`removed`; `reach` and the stored-permission projection
|
|
230
|
+
(`defineMcpToolPermissionMap`, `McpToolPermissionMap`,
|
|
231
|
+
`MCP_PERMISSION_ACTIONS`, `projectStoredPermissionActions`) are removed.
|
|
232
|
+
Owner verdicts and `delete_network` stay `human_only`; agent CRUD is
|
|
233
|
+
`agent_admin` and reachable only from a session.
|
|
234
|
+
|
|
235
|
+
### Changed
|
|
236
|
+
|
|
237
|
+
- `ResolvedToolContext` no longer carries `agentId`, so rate limiting and
|
|
238
|
+
owner-verdict checks key off the user and the session flag alone.
|
|
239
|
+
|
|
240
|
+
## 50.0.0 - 2026-09-05
|
|
241
|
+
|
|
242
|
+
### Removed
|
|
243
|
+
|
|
244
|
+
- **BREAKING — drop the IND-593 owner-approval proof port.** `update_opportunity`
|
|
245
|
+
send/accept/reject is an ordinary tool call gated by existing MCP/session auth.
|
|
246
|
+
Removed `ownerApprovalProof` from the public schema, plus
|
|
247
|
+
`OpportunityOwnerApprovalAuthority` and related public types,
|
|
248
|
+
`bindOwnerApprovalProvenance`, and `opportunityOwnerActionForStatus`. Owner
|
|
249
|
+
verdict tools (`accept_opportunity` / `reject_opportunity`) still require a
|
|
250
|
+
host-bound session (`context.isSessionAuth`).
|
|
251
|
+
|
|
252
|
+
## 49.0.1 - 2026-09-05
|
|
253
|
+
|
|
254
|
+
### Changed
|
|
255
|
+
|
|
256
|
+
- Documentation only. TSDoc and inline comments across `platform/database/` and
|
|
257
|
+
`internal/opportunities/` no longer call a network an "index".
|
|
258
|
+
`IMPLEMENTATION.md` drops the removed `indexer` dependency from its `Networks`
|
|
259
|
+
example and describes `createAssignmentGraph()` as it behaves today: no
|
|
260
|
+
scoring policy, rows written at score 1 with `mode: manual_override`.
|
|
261
|
+
`src/README.md` drops the Intent Indexer agent row, whose file
|
|
262
|
+
(`internal/intents/indexing/intent.indexer.ts`) no longer exists. No public
|
|
263
|
+
surface change.
|
|
264
|
+
|
|
265
|
+
## 49.0.0 - 2026-09-04
|
|
266
|
+
|
|
267
|
+
### Removed
|
|
268
|
+
|
|
269
|
+
- **BREAKING — the three intent↔network MCP tools were renamed.** External agents
|
|
270
|
+
must switch tool names; there is no alias or compatibility shim.
|
|
271
|
+
- `create_intent_index` → `add_intent_to_network`
|
|
272
|
+
- `read_intent_indexes` → `list_intent_networks`
|
|
273
|
+
- `delete_intent_index` → `remove_intent_from_network`
|
|
274
|
+
|
|
275
|
+
### Changed
|
|
276
|
+
|
|
277
|
+
- **BREAKING — host interfaces no longer call a network an "index".** The domain
|
|
278
|
+
renamed indexes to networks, but the ports a host implements still said
|
|
279
|
+
`Index`, so a host had to speak both vocabularies. Every such member is renamed
|
|
280
|
+
in place. Hosts must rename their implementations:
|
|
281
|
+
- `Database`/`UserDatabase`/`SystemDatabase` methods: `getOwnedIndexes` →
|
|
282
|
+
`getOwnedNetworks`, `getUserIndexIds` → `getUserNetworkIds`,
|
|
283
|
+
`getPublicIndexesNotJoined` → `getPublicNetworksNotJoined`,
|
|
284
|
+
`getMembersFromUserIndexes` → `getMembersFromUserNetworks`,
|
|
285
|
+
`getActiveIntentsAcrossIndexes` → `getActiveIntentsAcrossNetworks`,
|
|
286
|
+
`getIntentsInIndex` → `getIntentsInNetwork`, `getUserIntentsInIndex` →
|
|
287
|
+
`getUserIntentsInNetwork`, `getIntentsInIndexForMember` →
|
|
288
|
+
`getIntentsInNetworkForMember`, `getIntentIndexScores` →
|
|
289
|
+
`getIntentNetworkScores`, `deleteIntentIndexAssociations` →
|
|
290
|
+
`deleteIntentNetworkAssociations`, `isIntentAssignedToIndex` →
|
|
291
|
+
`isIntentAssignedToNetwork`, `unassignIntentFromIndex` →
|
|
292
|
+
`unassignIntentFromNetwork`, `isIndexOwner` → `isNetworkOwner`,
|
|
293
|
+
`removeMemberFromIndex` → `removeMemberFromNetwork`, `updateIndexSettings` →
|
|
294
|
+
`updateNetworkSettings`.
|
|
295
|
+
- Entity types: `OwnedIndex` → `OwnedNetwork`, `IndexMemberDetails` →
|
|
296
|
+
`NetworkMemberDetails`, `IndexedIntentDetails` → `NetworkIntentDetails`,
|
|
297
|
+
`UpdateIndexSettingsData` → `UpdateNetworkSettingsData`. The
|
|
298
|
+
`NetworkMembership.indexPrompt` field is now `networkPrompt`.
|
|
299
|
+
- Scope plumbing: `indexScope` is `networkScope` everywhere it appears —
|
|
300
|
+
`SystemDatabase.indexScope`, the `createSystemDatabase` /
|
|
301
|
+
`ScopedDepsFactory.create` third argument, `HydeSearchOptions.indexScope`,
|
|
302
|
+
`ChatToolRequest.indexScope`, and the intent/opportunity graph state channels.
|
|
303
|
+
- Tool context: `ResolvedToolContext.indexName`/`scopedIndex` are `networkName`/
|
|
304
|
+
`scopedNetwork`; `ToolRequestContext.indexName` is `networkName`.
|
|
305
|
+
- Graph registry keys: `graphs.index` → `graphs.network` and
|
|
306
|
+
`graphs.intentIndex` → `graphs.intentNetwork`. Their trace name changed from
|
|
307
|
+
`index` to `network`.
|
|
308
|
+
- `ChatContextAccessError.code` values `INDEX_NOT_FOUND` and
|
|
309
|
+
`INDEX_MEMBERSHIP_REQUIRED` are now `NETWORK_NOT_FOUND` and
|
|
310
|
+
`NETWORK_MEMBERSHIP_REQUIRED`.
|
|
311
|
+
- `resolveIndexNames` → `resolveNetworkNames`;
|
|
312
|
+
`DiscoveryNegotiation.indexContext` → `networkContext`.
|
|
313
|
+
- Presenter context: the `indexName` field returned by `gatherPresenterContext`
|
|
314
|
+
is `networkName`, which also fixes `focusedNetworkLabel` reading a field that
|
|
315
|
+
no longer existed and falling back to the network id.
|
|
316
|
+
- Agent-facing tool descriptions, scope-refusal messages, and `read_docs`
|
|
317
|
+
guidance now say "network" or "community" wherever they said "index".
|
|
318
|
+
- The intent assignment pipeline keeps its verb naming (`getIntentForIndexing`,
|
|
319
|
+
`indexer.graph.ts`, `IndexedIntent`): those describe assigning a signal, not
|
|
320
|
+
the community noun.
|
|
321
|
+
|
|
322
|
+
## 48.1.0 - 2026-09-04
|
|
323
|
+
|
|
324
|
+
### Changed
|
|
325
|
+
|
|
326
|
+
- **`read_docs` speaks networks, not indexes.** The topic key `indexes` is now
|
|
327
|
+
`networks` and its section is rewritten in network terms, so `topic=indexes`
|
|
328
|
+
no longer resolves to a section and falls back to the summary. MCP callers are
|
|
329
|
+
unaffected: that surface already served `communities-networks`.
|
|
330
|
+
- **Opportunity-graph log payloads renamed.** `targetIndexesCount` is
|
|
331
|
+
`targetNetworksCount` and the `indexes` key is `networks`, alongside the
|
|
332
|
+
surrounding trace strings. Log-scraping dashboards need updating.
|
|
333
|
+
|
|
334
|
+
## 48.0.0 - 2026-09-04
|
|
335
|
+
|
|
336
|
+
### Added
|
|
337
|
+
|
|
338
|
+
- **`Intents.clarify({ payload, answers? })` → `{ payload, questions }`.** One
|
|
339
|
+
stateless round of signal clarification: with no answers it returns the payload
|
|
340
|
+
untouched plus the questions worth asking; with answers it rewrites the payload
|
|
341
|
+
so those answers are stated in it and returns whatever is still open. Nothing
|
|
342
|
+
is stored, so skipping is always valid. `ClarifyAnswer`, `ClarifyInput`,
|
|
343
|
+
`ClarifyQuestion`, `ClarifyQuestionOption` and `ClarifyResult` are exported.
|
|
344
|
+
|
|
345
|
+
### Removed
|
|
346
|
+
|
|
347
|
+
- **BREAKING: the intake funnel is gone.** `IntakePack`, `IntakePackInput`,
|
|
348
|
+
`IntakePackQuestion`, `IntakePackQuestionOption`, `IntakeAnswer`, `IntakeRound`,
|
|
349
|
+
`FollowUpPlan`, `SynthesisInput` and `SynthesisResult` are removed along with
|
|
350
|
+
the pack generator and intake orchestrator. Clarification is `clarify` now, and
|
|
351
|
+
it holds no run state — hosts can drop their intake pack and run storage.
|
|
352
|
+
- **BREAKING: signals are no longer proposed before they are created.** The
|
|
353
|
+
dry-run branch of `create_intent`, the `intent_proposal` fence it emitted and
|
|
354
|
+
the `autoApprove` argument are gone. `create_intent({ description, networkIds })`
|
|
355
|
+
persists directly, so hosts can drop their proposal storage and their confirm
|
|
356
|
+
and reject endpoints.
|
|
357
|
+
- **BREAKING: networks are no longer assigned by a model.** `IntentNetworkIndexer`,
|
|
358
|
+
`IntentIndexingResult`, `Intents.indexIntent` and the evaluated branch of the
|
|
359
|
+
indexer graph are removed, and so is the threshold scoring behind them. A signal
|
|
360
|
+
reaches exactly the networks its owner names on create or links afterwards with
|
|
361
|
+
`create_intent_index`.
|
|
362
|
+
- **BREAKING: agents no longer have transports.** `AgentTransportRecord`,
|
|
363
|
+
`CreateTransportInput` and the `AgentDatabase` methods `createTransport`,
|
|
364
|
+
`deleteTransport`, `recordTransportFailure` and `recordTransportSuccess` are
|
|
365
|
+
removed, and `AgentWithRelations` no longer carries a `transports` array. No
|
|
366
|
+
delivery loop ever read the rows. Hosts can drop their `agent_transports`
|
|
367
|
+
storage.
|
|
368
|
+
- `createIntentSuggested` and `suggestedIntentDescription` from the opportunity
|
|
369
|
+
graph state. Nothing routed on them.
|
|
370
|
+
|
|
371
|
+
## 47.0.0 - 2026-09-03
|
|
372
|
+
|
|
373
|
+
### Removed
|
|
374
|
+
|
|
375
|
+
- **BREAKING: `'personal'` is no longer an agent type.** `AgentRecord.type` and
|
|
376
|
+
`CreateAgentInput.type` are now `'external' | 'system'`. The `personal` row was
|
|
377
|
+
the auto-provisioned per-user negotiator behind the in-process negotiation
|
|
378
|
+
loop; nothing reads it since that loop was deleted. Hosts must delete their
|
|
379
|
+
`personal` rows and shrink their own enum — user-registered agents are
|
|
380
|
+
`external`.
|
|
381
|
+
|
|
382
|
+
## 46.0.0 - 2026-09-03
|
|
383
|
+
|
|
384
|
+
### Removed
|
|
385
|
+
|
|
386
|
+
- **BREAKING: the question surface is gone.** `Question`, `QuestionPurpose`,
|
|
387
|
+
`QuestionPurposeSchema`, `QuestionStrategy`, `QuestionStrategySchema`,
|
|
388
|
+
`QuestionRecoverySnapshot` and `QuestionVoidedReason` are removed along with
|
|
389
|
+
`question.ts`, and so are the question-block exports (`QuestionBlockSchema`,
|
|
390
|
+
`QuestionBlockQuestionSchema`, `QuestionBlock`, `QuestionBlockQuestion`,
|
|
391
|
+
`ParsedQuestionMessage`, `parseQuestionMessage`, `serializeQuestionMessage`,
|
|
392
|
+
`questionBlockFixture`, `questionMessageFixture`, `questionProseFixture`).
|
|
393
|
+
The durable question system was retired generator-first; nothing produced,
|
|
394
|
+
stored or rendered these shapes any more. Hosts can drop their `questions`
|
|
395
|
+
storage with them.
|
|
396
|
+
- `UnderspecificationTypeSchema` and `UnderspecificationType` now come straight
|
|
397
|
+
from `protocol/schemas/underspecification.schema.ts`. The exported names and
|
|
398
|
+
types are unchanged; only the (never-contractual) internal module moved.
|
|
399
|
+
|
|
400
|
+
## 46.0.0 - 2026-09-03
|
|
401
|
+
|
|
402
|
+
### Removed
|
|
403
|
+
|
|
404
|
+
- **BREAKING: `upsertDiscoveryMatchCandidates` and `openCandidates` are replaced
|
|
405
|
+
by `openCounterparties(pairs)`.** Discovery no longer stages a scored pair
|
|
406
|
+
before opening it: it hands the host the pair and the host writes the
|
|
407
|
+
opportunity and its negotiation in one transaction, keyed on `pairKey`. Hosts
|
|
408
|
+
can drop their candidates table; the pair-uniqueness it enforced belongs on
|
|
409
|
+
the negotiation.
|
|
410
|
+
- **BREAKING: `DiscoveryMatchCandidate`, `CreateDiscoveryMatchCandidateData` and
|
|
411
|
+
`DiscoveryMatchCandidateStatus` are gone.** `CreateIntentCounterpartyData`
|
|
412
|
+
replaces the create shape as a call payload rather than a stored entity.
|
|
413
|
+
|
|
414
|
+
## 45.0.0 - 2026-09-03
|
|
415
|
+
|
|
416
|
+
### Added
|
|
417
|
+
|
|
418
|
+
- **`NegotiationContextDatabase`** (`platform/database/negotiation.ts`), with
|
|
419
|
+
`NegotiationContextRecord`, `NegotiationContextTurn` and
|
|
420
|
+
`NegotiationContextOutcome`. The host reads one negotiation record and its
|
|
421
|
+
turn log; the loader turns that into the prompt block and the negotiating
|
|
422
|
+
chip. It replaces every task-shaped read the old loader performed.
|
|
423
|
+
- **`OpportunityGraphDatabase.openCandidates`** returns `OpenedNegotiation[]`.
|
|
424
|
+
Discovery now opens the opportunity and its negotiation record together, so
|
|
425
|
+
the graph never leaves a scored candidate without a record to negotiate in.
|
|
426
|
+
|
|
427
|
+
### Removed
|
|
428
|
+
|
|
429
|
+
- **BREAKING: `NegotiationGraphDatabase` is gone**, along with
|
|
430
|
+
`NegotiationTurnSchema`, the `negotiation-evidence` module and its exports,
|
|
431
|
+
the negotiation digest schema, and `CreateAndOpenResult`. Index is the server
|
|
432
|
+
for a negotiation: it validates turn order, appends the turn and computes the
|
|
433
|
+
settlement, so there is no in-process graph left to give a port.
|
|
434
|
+
- **BREAKING: `listPendingCandidatesForIntent` is replaced by `openCandidates`**
|
|
435
|
+
on the discovery database port.
|
|
436
|
+
- **BREAKING: `'stalled'` is gone from `OpportunityStatus`.** It was the
|
|
437
|
+
turn-cap outcome of the A2A task loop; the negotiation record has two
|
|
438
|
+
outcomes and a close, so nothing produces it.
|
|
439
|
+
|
|
440
|
+
## 44.0.0 - 2026-09-03
|
|
441
|
+
|
|
442
|
+
### Removed
|
|
443
|
+
|
|
444
|
+
- **BREAKING: `NegotiationRoundLogDatabase`, `NegotiationRoundLogEventKind` and
|
|
445
|
+
`NegotiationRoundLogEventRecord` are gone.** The port was orphaned when the
|
|
446
|
+
in-process negotiation graph and its `foldNegotiationRoundLog` were deleted:
|
|
447
|
+
nothing composed it into `NegotiationGraphDatabase` and no host implemented
|
|
448
|
+
its two methods. Hosts that declared them can delete those implementations
|
|
449
|
+
along with their `negotiation_round_log_events` storage.
|
|
450
|
+
|
|
451
|
+
## 43.0.0 - 2026-09-02
|
|
452
|
+
|
|
453
|
+
### Removed
|
|
454
|
+
|
|
455
|
+
- **BREAKING: `McpAuthInputSchema` no longer accepts `telegramHandle` or
|
|
456
|
+
`telegramUsername`.** The MCP server stops reading the `x-telegram-handle` and
|
|
457
|
+
`x-telegram-username` headers, and the host no longer binds a Telegram handle
|
|
458
|
+
to an account at authentication time. Telegram on a user profile is now only a
|
|
459
|
+
social link, so `telegram-handle.ts` and `social-label.ts` are unchanged.
|
|
460
|
+
|
|
461
|
+
## 42.0.0 - 2026-09-02
|
|
462
|
+
|
|
463
|
+
### Removed
|
|
464
|
+
|
|
465
|
+
- **BREAKING: the premises capability is gone.** `create_premise`,
|
|
466
|
+
`read_premises`, `update_premise`, and `retract_premise` are no longer
|
|
467
|
+
registered; `PremiseGraphFactory`, `PremiseGraphDatabase`, `PremiseRecord`,
|
|
468
|
+
`OpportunityActor.premise`, and every premise method on the host database
|
|
469
|
+
ports are removed. Matching is intent-only: `HydeTargetCorpus` drops
|
|
470
|
+
`'premises'`, the `query_premise` evidence kind and the
|
|
471
|
+
`sourcePremiseId`/`candidatePremiseId` candidate fields are gone, and
|
|
472
|
+
`manage:premises` is no longer a permission action. The protocol README drops
|
|
473
|
+
**Premise** as an entity: context stands on its own, and candidate generation
|
|
474
|
+
no longer lists premise-to-premise as a strategy.
|
|
475
|
+
- **BREAKING: opportunity delivery is gone.** `confirm_opportunity_delivery`,
|
|
476
|
+
the `DeliveryLedger` port, `getOrCreateDeliveryCardBatch`,
|
|
477
|
+
`buildDeliveryCardPresentationCacheKey`, the `isDeliveryAgent` identity flag,
|
|
478
|
+
and digest mode (`includeDigestMarkers`, `selectDigestCandidates`,
|
|
479
|
+
presenter `digestSummary`) are removed. Opportunity statuses are unchanged.
|
|
480
|
+
- **BREAKING: `read_activity_summary` is gone**, along with the activity
|
|
481
|
+
projection and the `UserDatabase.getAgentActivitySummary` port.
|
|
482
|
+
|
|
483
|
+
No aliases or compatibility shims: hosts must drop the deleted ports.
|
|
484
|
+
|
|
485
|
+
## 41.0.0 - 2026-09-02
|
|
486
|
+
|
|
487
|
+
### Removed
|
|
488
|
+
|
|
489
|
+
- **BREAKING: `SYSTEM_AGENT_IDS.chatOrchestrator` is gone.** The only remaining
|
|
490
|
+
well-known system agent is `negotiator`. `AgentDatabase.getSystemAgentIds()`
|
|
491
|
+
no longer returns a chat-orchestrator id.
|
|
492
|
+
- **BREAKING: the in-process personal agent is gone.** `PersonalAgentGraph` and
|
|
493
|
+
everything it needed — its judgment, prompt, act types, activity port, match
|
|
494
|
+
refs and the `personal-agent.e2e` spec — are deleted. Index no longer runs an
|
|
495
|
+
agent; a host that wants one builds it as a client over REST/MCP.
|
|
496
|
+
- **BREAKING: `ChatGraph` and the whole chat capability are gone.**
|
|
497
|
+
`ChatGraphFactory`, `ChatAgent`, the personas (`SIGNAL_PERSONA`,
|
|
498
|
+
`ONBOARDING_PERSONA`, `withPersona`), the streamer, suggester, summarizer,
|
|
499
|
+
title generator, interrupt classifier, question-dedup, chat state/tools/utils
|
|
500
|
+
and the chat-streaming types no longer exist. There is no H2A chat runtime in
|
|
501
|
+
the protocol.
|
|
502
|
+
- **BREAKING: `NegotiationGraph` and the negotiation MCP tools are gone.**
|
|
503
|
+
`NegotiationGraphFactory`, the turn author, the round-reflect enqueue, the
|
|
504
|
+
`IndexNegotiator` agent, the insight generator and summarizer, and the
|
|
505
|
+
`list_negotiations` / `get_negotiation` / `respond_to_negotiation` /
|
|
506
|
+
`answer_pending_question` tools are all deleted. Negotiation turn shapes and
|
|
507
|
+
the `NegotiationGraphDatabase` port remain, because the host still persists
|
|
508
|
+
and reads negotiation conversations.
|
|
509
|
+
- **BREAKING: host ports for the deleted runtimes are gone** —
|
|
510
|
+
`AgentDispatcher`, `ChatSessionReader`, `ChatSummaryReader`,
|
|
511
|
+
`ChatMessageWriter`, `NegotiationSummaryReader`, `MintConnectLink`, and
|
|
512
|
+
`AgentRepositoryPort.findAuthorizedAgents`.
|
|
513
|
+
- Specs are down to three: `capabilities/tests/intents`,
|
|
514
|
+
`internal/opportunities/tests/opportunity.graph`, and
|
|
515
|
+
`internal/premises/tests/premise.decomposer`.
|
|
516
|
+
|
|
517
|
+
### Changed
|
|
518
|
+
|
|
519
|
+
- **BREAKING: `ChatGraphCompositeDatabase` is `CompositeToolDatabase`.** The
|
|
520
|
+
type outlived the graph it was named after; it is still the composite the
|
|
521
|
+
host passes to the tool factory.
|
|
522
|
+
- **BREAKING: `OpportunityGraphFactory` drops two constructor parameters.** The
|
|
523
|
+
`matchesReady` and `agentDispatcher` slots are gone, so `thresholdOverrides`
|
|
524
|
+
moves from the eighth positional argument to the sixth.
|
|
525
|
+
|
|
526
|
+
**Kept:** intents, premises, networks, opportunities (including
|
|
527
|
+
`OpportunityGraphFactory` discovery into candidates), radar, HyDE, the agent
|
|
528
|
+
registry tools, the owner-verdict tools, and the MCP server shell over what
|
|
529
|
+
remains.
|
|
530
|
+
|
|
531
|
+
## 40.0.0 - 2026-08-29
|
|
532
|
+
|
|
533
|
+
### Changed
|
|
534
|
+
|
|
535
|
+
- **BREAKING: `VectorStoreOption.filter` is `Record<string, unknown>`.** It was
|
|
536
|
+
`Record<string, any>`. Callers passing a filter are unaffected; host
|
|
537
|
+
implementations of the `VectorStore`/`Embedder` port that read values off
|
|
538
|
+
`options.filter` must now narrow them instead of relying on `any`.
|
|
539
|
+
|
|
540
|
+
## 39.0.0 - 2026-08-29
|
|
541
|
+
|
|
542
|
+
### Changed
|
|
543
|
+
|
|
544
|
+
- **BREAKING: the intent follow-up port is no longer named after a queue.**
|
|
545
|
+
`IntentGraphQueue` is `IntentFollowUp` and `IntentGraphQueueScope` is
|
|
546
|
+
`IntentFollowUpScope`, both now in `platform/runtime/follow-up.ts`. The
|
|
547
|
+
methods lose their job wording: `addGenerateHydeJob` → `generateHyde`,
|
|
548
|
+
`addDeleteHydeJob` → `deleteHyde`, `addResumeDiscoveryJob` →
|
|
549
|
+
`resumeDiscovery`. `IntentsDeps.queue` is `IntentsDeps.followUp` and the
|
|
550
|
+
agent tool context's `intentQueue` is `intentFollowUp`. Behaviour is
|
|
551
|
+
unchanged; the host has run this work in-process since the queue system was
|
|
552
|
+
removed. Update call sites by renaming — there is no compatibility shim.
|
|
553
|
+
|
|
554
|
+
## 38.0.1 - 2026-08-28
|
|
555
|
+
|
|
556
|
+
### Removed
|
|
557
|
+
- Delete `docs/` and every spec except five (`capabilities/tests/intents`,
|
|
558
|
+
`capabilities/tests/negotiations.e2e`, `capabilities/tests/personal-agent.e2e`,
|
|
559
|
+
`internal/opportunities/tests/opportunity.graph`,
|
|
560
|
+
`internal/premises/tests/premise.decomposer`), along with
|
|
561
|
+
`scripts/tests/` and `scripts/architecture/tests/`. The `test:architecture`
|
|
562
|
+
script is gone and `architecture:check` no longer calls it; the three
|
|
563
|
+
`architecture:*` scripts are unchanged and still gate the package.
|
|
564
|
+
`LIVE_MODEL_SPECS` drops two entries that no longer existed. No source or
|
|
565
|
+
public-surface change: `src/index.ts` exports exactly what it did in 38.0.0.
|
|
566
|
+
|
|
567
|
+
## 37.0.0 - 2026-08-27
|
|
568
|
+
|
|
569
|
+
### Breaking
|
|
570
|
+
|
|
571
|
+
- **`read_premises(userId)` is scoped to shared networks.** Cross-user premise
|
|
572
|
+
reads are denied unless the caller and target share at least one network
|
|
573
|
+
membership, and return only the premises assigned to a shared network — a
|
|
574
|
+
premise its author never put into a network you are both in stays private.
|
|
575
|
+
`includeRetracted` is own-only.
|
|
576
|
+
- **`get_negotiation` redacts counterparty continue-turn `reasoning`.** The
|
|
577
|
+
shared thread still exposes `message`; each seat keeps its own `reasoning`.
|
|
578
|
+
Pause payloads remain private to the pausing seat (now also on the presenter
|
|
579
|
+
loader path).
|
|
580
|
+
|
|
581
|
+
## 36.0.0 - 2026-08-24
|
|
582
|
+
|
|
583
|
+
### Breaking
|
|
584
|
+
|
|
585
|
+
- **Intent matches and negotiations are isolated by their exact intent pair.**
|
|
586
|
+
`persistIntentScopedOpportunityIfNetworkEligible` no longer returns the
|
|
587
|
+
`pair_active_negotiation` conflict: any opportunity for the same two intent
|
|
588
|
+
seats deduplicates persistence. Hosts must allow different intent
|
|
589
|
+
pairs between the same users to persist and negotiate independently; task
|
|
590
|
+
creation remains idempotent per opportunity. Counterparty seats are bound
|
|
591
|
+
from authoritative discovery candidates rather than evaluator-generated
|
|
592
|
+
intent IDs, and intent-scoped persistence fails closed on an unbound seat.
|
|
593
|
+
|
|
594
|
+
- **Negotiation drains are keyed by durable task generations and tasks bind
|
|
595
|
+
both seats at creation.** `NegotiationTaskMetadata` gains
|
|
596
|
+
`drainGeneration`; `NegotiationGraphDatabase.openNegotiationTask` accepts
|
|
597
|
+
the complete `seats` map; `NegotiationRoundReflectJobData` gains
|
|
598
|
+
`generation`; `NegotiationTaskState` includes the active `submitted` state;
|
|
599
|
+
and `negotiationRoundReflectJobId` now requires its generation. Reopening a
|
|
600
|
+
paused task advances its generation, so one pause is deduplicated exactly
|
|
601
|
+
once without suppressing a later pause in the same round.
|
|
602
|
+
|
|
603
|
+
### Changed
|
|
604
|
+
|
|
605
|
+
- PersonalAgent intent turns reload durable negotiation state after each
|
|
606
|
+
action, cannot finish while an own `ready_for_verdict` pause remains, and
|
|
607
|
+
expose counterparty pauses only through canonical public status prose.
|
|
608
|
+
- Only the seat owning a `ready_for_verdict` pause may resolve it;
|
|
609
|
+
counterparty-owned pauses cannot be re-opened, and kickoff strategy copy
|
|
610
|
+
cannot bypass canonical public status narration.
|
|
611
|
+
- The negotiation watchdog retries reflect delivery for durable
|
|
612
|
+
`ready_for_verdict` pauses, and intent-cycle projections count both
|
|
613
|
+
`submitted` and `working` tasks as active.
|
|
614
|
+
- Verdict completion now atomically records the outcome, completes the task,
|
|
615
|
+
and preserves any concurrent terminal human decision. Post-verdict reflect
|
|
616
|
+
delivery remains durably marked until it succeeds, terminal owner actions
|
|
617
|
+
left beside active tasks are recovered by the watchdog, and bounded sweeps
|
|
618
|
+
rotate checked rows so newer pauses cannot starve.
|
|
619
|
+
- Scheduled opportunity expiry now closes any active negotiation through a
|
|
620
|
+
distinct system lane, without fabricating an owner verdict, so expired work
|
|
621
|
+
cannot hold either seat's round open.
|
|
622
|
+
|
|
623
|
+
## 35.0.0 - 2026-08-24
|
|
624
|
+
|
|
625
|
+
### Breaking
|
|
626
|
+
|
|
627
|
+
- **PersonalAgent questions use the canonical structured question contract.**
|
|
628
|
+
`message_user.options` is replaced by `message_user.questions` on decided
|
|
629
|
+
and executed acts and on the conversation delivery port. Questions are
|
|
630
|
+
safety-checked and delivered separately from the message introduction so
|
|
631
|
+
clients can render the guided question UI directly. The exported
|
|
632
|
+
`normalizeMessageOptions` helper is replaced by `normalizeMessageQuestions`.
|
|
633
|
+
|
|
634
|
+
### Added
|
|
635
|
+
|
|
636
|
+
- `PersonalAgentActivity` and `PersonalAgentActivityPort` provide bounded,
|
|
637
|
+
user-facing progress updates for live intent turns without exposing internal
|
|
638
|
+
identifiers, model reasoning, or private context.
|
|
639
|
+
|
|
640
|
+
## 34.0.1 - 2026-08-24
|
|
641
|
+
|
|
642
|
+
### Changed
|
|
643
|
+
|
|
644
|
+
- All canonical agent defaults now use Google Gemini 3.7 Flash with its
|
|
645
|
+
required low reasoning effort. Non-Gemini model overrides do not receive
|
|
646
|
+
Gemini-specific reasoning parameters.
|
|
647
|
+
|
|
648
|
+
## 34.0.0 - 2026-08-24
|
|
649
|
+
|
|
650
|
+
### Breaking
|
|
651
|
+
|
|
652
|
+
- **PersonalAgent intent turns use one sequential judgment choice at a time.**
|
|
653
|
+
`PersonalAgentJudgment.decide(context)` and
|
|
654
|
+
`PersonalAgentJudgment.reply(context, executed)` are replaced by
|
|
655
|
+
`next(context, executed, nonDurable?)`. Each call returns one
|
|
656
|
+
`PersonalAgentDecidedAct`; completed effects and refused irreversible calls
|
|
657
|
+
inform the next choice before the turn ends with `message_user`.
|
|
658
|
+
- **The dedicated `ask` act is removed.** Questions are ordinary
|
|
659
|
+
`message_user` responses, so an unresolved question about one matter no
|
|
660
|
+
longer blocks an independent action on another. `PersonalAgentDecidedAct`
|
|
661
|
+
and `PersonalAgentExecutedAct` no longer include `ask`, and executed
|
|
662
|
+
`message_user` acts no longer carry reply-stage `stage` or `fallback`
|
|
663
|
+
fields.
|
|
664
|
+
- **Executed kickoff results gain required attempt accounting.** Every
|
|
665
|
+
`PersonalAgentExecutedAct` with `tool: 'kickoff'` now includes `attempted`
|
|
666
|
+
and `failed` alongside `opened`.
|
|
667
|
+
- **The separate reply-stage API is deleted.** Removed root exports:
|
|
668
|
+
`PERSONAL_AGENT_REPLY_FALLBACK`, `renderPersonalAgentReplyStage`,
|
|
669
|
+
`validateDecidedActs`, `PersonalAgentReply`, and
|
|
670
|
+
`PersonalAgentReplyFallbackReason`. Use the singular `validateDecidedAct`
|
|
671
|
+
for one choice.
|
|
672
|
+
|
|
673
|
+
### Added
|
|
674
|
+
|
|
675
|
+
- `PersonalAgentNonDurableObservation`, the feedback shape for an
|
|
676
|
+
irreversible tool choice refused before any write or ledger entry.
|
|
677
|
+
|
|
678
|
+
### Changed
|
|
679
|
+
|
|
680
|
+
- Intent-scope events now share one bounded, result-informed conversational
|
|
681
|
+
tool loop. Repeated irreversible calls are refused against the turn's
|
|
682
|
+
snapshot, and a failure after durable work or tool-budget exhaustion ends
|
|
683
|
+
with honest terminal copy instead of retrying earlier effects.
|
|
684
|
+
|
|
685
|
+
## 33.0.0 - 2026-08-24
|
|
686
|
+
|
|
687
|
+
### Breaking
|
|
688
|
+
|
|
689
|
+
- **External negotiation responses use `NegotiationAuthoredTurn` directly.**
|
|
690
|
+
`respond_to_negotiation` accepts only `outreach`, `counter`, `question`,
|
|
691
|
+
`pause(needs_principal)`, and `pause(ready_for_verdict)`; it never accepts
|
|
692
|
+
terminal verbs. The retired `HermesNegotiationActionSchema` /
|
|
693
|
+
`HermesNegotiationAction` action vocabulary is removed. A counterparty that
|
|
694
|
+
wants out must pause `ready_for_verdict` with a `reject` recommendation for
|
|
695
|
+
its own PersonalAgent to decide.
|
|
696
|
+
- **`NegotiationGraphDatabase` gains `openNegotiationTask`.** Graph opens now
|
|
697
|
+
require one durable atomic open-or-return-live-task write; hosts must
|
|
698
|
+
revalidate eligibility there and return `{ task, created }` so a concurrent
|
|
699
|
+
opener can stop without authoring duplicate opening outreach.
|
|
700
|
+
|
|
701
|
+
## 32.0.0 - 2026-08-24
|
|
702
|
+
|
|
703
|
+
### Breaking
|
|
704
|
+
|
|
705
|
+
- **`NegotiationGraph` refuses to open an opportunity whose introducers have
|
|
706
|
+
not all approved it.** The gate now lives on the write, not only where
|
|
707
|
+
discovery decides which signals to wake, so no caller can reach past it.
|
|
708
|
+
- **New negotiation pause reason `open_failed`.** `NEGOTIATION_PAUSE_REASONS`
|
|
709
|
+
gains it, and `{ negotiationId, pause }` now accepts
|
|
710
|
+
`NegotiationSystemPauseReason` (`'counterparty_silent' | 'open_failed'`)
|
|
711
|
+
rather than the single literal. A kickoff whose open failed after `init`
|
|
712
|
+
created the task compensates it into this pause, so the round's active count
|
|
713
|
+
can still reach zero. Unlike `turn_cap` it stays re-kickable.
|
|
714
|
+
- **A negotiation binds a signal PER SEAT.** `NegotiationTaskMetadata.intentId`
|
|
715
|
+
and `.round` are replaced by `seats: Record<string, NegotiationSeatBinding>`
|
|
716
|
+
keyed by intent id (`{ userId, round }`), and `setNegotiationRound` becomes
|
|
717
|
+
`bindNegotiationSeat(taskId, intentId, binding)`. Both sides' IS-A can now
|
|
718
|
+
see and terminate a negotiation, which the loop's
|
|
719
|
+
`ready_for_verdict(reject)` rule requires. The resume input gains a required
|
|
720
|
+
`byUserId`, and the negotiator-scope `intentId` is optional (a seat that has
|
|
721
|
+
not kicked off has no binding). New export: `NegotiationSeatBinding`.
|
|
722
|
+
- **A negotiation's brief is now PER SEAT.** `NegotiationTaskRow.brief: string`
|
|
723
|
+
becomes `briefs: Record<string, string>` keyed by the seat's userId,
|
|
724
|
+
`createNegotiationTask` takes `briefs`, and `setNegotiationBrief` takes the
|
|
725
|
+
seat's `userId`. A seat with no brief has its own agent author one at its
|
|
726
|
+
first turn (`PersonalAgentJudgment.seatBrief`), and `get_negotiation` returns
|
|
727
|
+
the caller's own brief only. The `brief` on the graph's open/resume inputs is
|
|
728
|
+
the INITIATING seat's, never the counterparty's.
|
|
729
|
+
- **`NegotiationGraphDatabase` gains `getPausedNegotiationTasksForIntent`** —
|
|
730
|
+
the signal-scoped read of every paused, unresolved negotiation. Reflect
|
|
731
|
+
reasons over that, not over one round: a negotiation a later kickoff left
|
|
732
|
+
behind keeps its old round, and a round-scoped read hid it from every future
|
|
733
|
+
verdict.
|
|
734
|
+
- **`NegotiationGraphDatabase.getIntentNegotiationRound` returns
|
|
735
|
+
`kickoffStartedAt`** alongside `round` and `roundSize`, and
|
|
736
|
+
`bumpIntentNegotiationRound` must stamp it in the same write. A marker set
|
|
737
|
+
with a null size is the one signature of a kickoff that died mid-round;
|
|
738
|
+
inferring that from the null size alone matched every intent that predates
|
|
739
|
+
round stamping.
|
|
740
|
+
- **`ToolDeps`/`McpToolDeps` gain `matchesReady`**, which every host must set:
|
|
741
|
+
the OpportunityGraph `tool.factory` builds ends its matches_ready edge at
|
|
742
|
+
`END` without it, so a chat- or MCP-run discovery persists matches nobody is
|
|
743
|
+
woken for.
|
|
744
|
+
- **`PersonalAgentDeps` gains `wakeForMatches`** — the agent wakes its own
|
|
745
|
+
signal again for a discovery batch that landed after the turn read its match
|
|
746
|
+
list.
|
|
747
|
+
- **The retired `queueNegotiateExisting` host callback is removed** from
|
|
748
|
+
`ToolDeps` and `OpportunityGraphFactory`. Approving the final introducer
|
|
749
|
+
gate emits `matches_ready` for the source participant's bound signal; it
|
|
750
|
+
never directly opens or resumes a negotiation.
|
|
751
|
+
|
|
752
|
+
- **AgentGraph: one PersonalAgent, routed on the shape of its input.** New
|
|
753
|
+
`PersonalAgentGraphFactory` — `{ userId }` is global (a graph-level input
|
|
754
|
+
error, deferred), `{ userId, intentId, event: 'user_message' | 'matches_ready'
|
|
755
|
+
| 'all_paused' }` is the intent scope (IS-A), `{ userId, intentId,
|
|
756
|
+
negotiationId }` is one negotiator turn. `matches_ready` and `all_paused`
|
|
757
|
+
are ONE node — look at the state, maybe ask, else act — differing only in
|
|
758
|
+
what ACT does. IS-A's verbs are `message_user`, `ask`, `kickoff`, `promote`,
|
|
759
|
+
`reject`, `note_dossier`, `retire_dossier`, `accept_opportunity`; there is
|
|
760
|
+
no `wait`. Asking BLOCKS acting: a turn that asks executes no verdicts and
|
|
761
|
+
starts no negotiations. The host implements the ports (signal DM, dossier,
|
|
762
|
+
act ledger, reply transport, the owner's accept path, matches list).
|
|
763
|
+
- **The interim `NegotiationAuthor` is deleted.** `NegotiationGraphDeps.author`
|
|
764
|
+
is now a required `NegotiationTurnAuthor` port taking ids only
|
|
765
|
+
(`{ negotiationId, userId, intentId }`); production binds it to the
|
|
766
|
+
PersonalAgent in negotiation scope, which reads the brief and thread itself.
|
|
767
|
+
Removed exports: `NegotiationAuthor`, `NegotiationAuthorInput`.
|
|
768
|
+
- **Discovery no longer opens negotiations.** The opportunity graph's
|
|
769
|
+
`negotiate` node is replaced by a `matches_ready` node that emits ONE event
|
|
770
|
+
per signal per persisted batch through the new `MatchesReadyFn` host
|
|
771
|
+
callback; the signal's PersonalAgent decides whether to reach out at all.
|
|
772
|
+
`OpportunityGraphFactory`'s sixth constructor argument changes from
|
|
773
|
+
`negotiationGraph` to `matchesReady`, and `ToolFactory`/`ToolDeps` gain
|
|
774
|
+
`matchesReady`. The tool factory no longer builds a second, reflect-less
|
|
775
|
+
negotiation graph: without the host's own composition there is no
|
|
776
|
+
negotiation graph in that context at all.
|
|
777
|
+
- **The all-paused → reflect trigger is gated on a round-size stamp.**
|
|
778
|
+
`NegotiationRoundReflectJobData` gains `userId` (the signal's owner, so the
|
|
779
|
+
consumer can invoke the PersonalAgent). `NegotiationGraphDatabase` gains
|
|
780
|
+
`getNegotiationTasksForIntentRound`, `getIntentNegotiationRound` and
|
|
781
|
+
`stampIntentNegotiationRoundSize`, and `bumpIntentNegotiationRound` must now
|
|
782
|
+
CLEAR the size stamp. Until kickoff stamps the size — after every parallel
|
|
783
|
+
open has settled — the check is a no-op, so an early first pause can no
|
|
784
|
+
longer dedupe away the round's genuine reflect. New export:
|
|
785
|
+
`maybeEnqueueRoundReflect`.
|
|
786
|
+
|
|
787
|
+
### Added
|
|
788
|
+
|
|
789
|
+
- `isSafeAgentMessageProse`, the identifier-leak gate every piece of
|
|
790
|
+
agent-authored prose passes before it is persisted or streamed.
|
|
791
|
+
- `chunkReplyText` and `PERSONAL_AGENT_REPLY_FALLBACK`, moved from the host
|
|
792
|
+
with the reply stage.
|
|
793
|
+
|
|
794
|
+
## 31.0.0 - 2026-08-24
|
|
795
|
+
|
|
796
|
+
### Breaking
|
|
797
|
+
|
|
798
|
+
### Fixed
|
|
799
|
+
|
|
800
|
+
- **`NegotiationGraph`'s `resolve` no longer writes over an already-terminal
|
|
801
|
+
opportunity status.** An owner verdict (Radar skip/accept,
|
|
802
|
+
`PATCH /opportunities/:id/status`, the DM's accept/reject tools) writes
|
|
803
|
+
`accepted` / `rejected` itself — a user action outside the negotiation loop
|
|
804
|
+
by design — and then calls `resolve` to CLOSE the negotiation, because a
|
|
805
|
+
terminal opportunity whose task stays `working` holds its round open forever
|
|
806
|
+
and the round's reflect job never fires. Rewriting the status inside
|
|
807
|
+
`resolve` would have downgraded that `accepted` back to `pending` and
|
|
808
|
+
re-fired the actionable notification for a match the owner had already
|
|
809
|
+
accepted.
|
|
810
|
+
|
|
811
|
+
## 30.0.0 - 2026-08-24
|
|
812
|
+
|
|
813
|
+
### Changed
|
|
814
|
+
|
|
815
|
+
- **One PersonalAgent persona.** The signal, onboarding, and negotiator chat
|
|
816
|
+
personas collapse into a single `createPersonalAgentPersona(identity)`
|
|
817
|
+
factory with `PERSONAL_AGENT_PERSONA_ID = 'personal'`. What a turn may do is
|
|
818
|
+
derived from the session's resolved scope context, never from a persona id;
|
|
819
|
+
the onboarding prompt/toolset is a fragment selected by incomplete-onboarding
|
|
820
|
+
session state on truly unscoped sessions only. Removed exports:
|
|
821
|
+
`SIGNAL_PERSONA_ID`, `createSignalPersona`, `ONBOARDING_PERSONA_ID`,
|
|
822
|
+
`createOnboardingPersona`, `NEGOTIATOR_PERSONA_ID`, `PersonalAgentChat`,
|
|
823
|
+
`PersonalAgentChatDeps`. The negotiator persona (prompt, chat toolset, and
|
|
824
|
+
its `remember`/`forget` chat tools plus the `negotiatorMemoryTools` host
|
|
825
|
+
port) is deleted outright: every intent-scoped DM turn is IntentAgent-owned
|
|
826
|
+
host-side, so no chat persona exists for that scope. Tool allowlists and
|
|
827
|
+
narrowing are unchanged in content.
|
|
828
|
+
|
|
829
|
+
## 29.0.0 - 2026-08-23
|
|
830
|
+
|
|
831
|
+
### Breaking
|
|
832
|
+
|
|
833
|
+
- **NegotiationGraph rewritten as a single write path.** Every write to a
|
|
834
|
+
negotiation now goes through one graph, routed on the shape of its invoke
|
|
835
|
+
input — no `operationMode`: `{ opportunityId, brief, intentId }` opens,
|
|
836
|
+
`{ negotiationId, brief }` resumes, `{ negotiationId, turn }` applies a
|
|
837
|
+
submitted turn (internal, external agent, or timeout, all through the same
|
|
838
|
+
`apply` sink), `{ negotiationId, pause: 'counterparty_silent' }` is a
|
|
839
|
+
timeout, `{ negotiationId, verdict: 'pending' | 'reject' }` is the only
|
|
840
|
+
terminal write, `{ negotiationId }` reads.
|
|
841
|
+
- **The negotiator no longer terminates a negotiation.** `IndexNegotiator`
|
|
842
|
+
and its stances, deadlock shift, checklist gate, conclusion floor, decline
|
|
843
|
+
law, copy-loop guard, turn cap and park window as *outcomes* are deleted.
|
|
844
|
+
A turn is now one of `outreach | counter | question` (continue) or
|
|
845
|
+
`pause(counterparty_silent | needs_principal | ready_for_verdict, payload)`.
|
|
846
|
+
There is no `accept`, `decline`, or `withdraw` on the turn surface — a side
|
|
847
|
+
that wants out pauses `ready_for_verdict(reject)`. `resolve` (writing
|
|
848
|
+
`pending`/`reject` to the opportunity) is the only way a negotiation ends,
|
|
849
|
+
and nothing calls it yet in this release; negotiations pause and wait until
|
|
850
|
+
the caller that will do so (IS-A / AgentGraph) lands.
|
|
851
|
+
- **The interim internal turn author is `NegotiationAuthor`**, a single
|
|
852
|
+
structured-output call constrained to the verb schema in
|
|
853
|
+
`negotiation.turn.ts`, prompted from the brief and the thread so far. It
|
|
854
|
+
replaces `IndexNegotiator` for this release only; AgentGraph replaces it in
|
|
855
|
+
turn.
|
|
856
|
+
- **The A2A conversation is per negotiation, not per pair.** A negotiation is
|
|
857
|
+
its own conversation and its own task. There is no seeded prior-pair
|
|
858
|
+
dialogue, no `priorAttribution`, no conversation lock.
|
|
859
|
+
- **`respond_to_negotiation` takes a turn, not an accept/decline/withdraw
|
|
860
|
+
action.** External agents (Hermes, MCP) submit the same verbs as the
|
|
861
|
+
internal author, validated the same way. `consult` and the second
|
|
862
|
+
`ask_user` park are removed; an external agent needing its principal
|
|
863
|
+
submits `pause(needs_principal, …)` like everyone else.
|
|
864
|
+
- **Removed exports**: `IndexNegotiator`, `negotiateCandidates`,
|
|
865
|
+
`NegotiationGraphFactory`'s old constructor shape (now a single
|
|
866
|
+
`NegotiationGraphDeps` object), `UserNegotiationContext`,
|
|
867
|
+
`NegotiationAction`, `NegotiationSeat`, `NegotiationConsultationReason(Schema)`,
|
|
868
|
+
`resumeParkedNegotiation`, `NegotiationAnswerConsumptionPorts`,
|
|
869
|
+
`createNegotiationAnswerTools`, `NegotiationCounterpartyBinding`,
|
|
870
|
+
`expectedNegotiationSpeaker`, `negotiationScopeKey`,
|
|
871
|
+
`NegotiationContinuationTimeoutIdentity`, `AMBIENT_PARK_WINDOW_MS`,
|
|
872
|
+
`ASK_USER_WINDOW_MS`, `ASK_USER_LOCK_SLACK_MS`,
|
|
873
|
+
`NEGOTIATION_MAX_TURNS_CHAT`, `countOpenPreContactConsults`,
|
|
874
|
+
`PreContactConsultTaskRow`, `InChatNegotiationQuestionDelivery`, and the
|
|
875
|
+
negotiation checklist/deadlock/stance/consultation-policy modules.
|
|
876
|
+
- **New exports**: `NegotiationTurnSchema` and its verb/pause-reason/verdict
|
|
877
|
+
types, `NegotiationAuthor`, `negotiationRoundReflectJobId` and
|
|
878
|
+
`NegotiationRoundReflectEnqueueFn` (the all-paused → reflect trigger — the
|
|
879
|
+
reflect consumer itself is a stub until AgentGraph lands), the rewritten
|
|
880
|
+
`NegotiationGraphDatabase` port (`brief` is now a dedicated field;
|
|
881
|
+
`metadata` carries `intentId`/`round`/`pause`).
|
|
882
|
+
- **`OpportunityGraph`'s `negotiateNode`** now invokes
|
|
883
|
+
`{ opportunityId, intentId, brief }` for every persisted opportunity — no
|
|
884
|
+
selection, no cap. This release's brief is a minimal deterministic string
|
|
885
|
+
built from the trigger intent; IS-A authors real briefs in the next
|
|
886
|
+
release. `negotiateCandidates`, `compensateTasklessNegotiatingOpportunity`,
|
|
887
|
+
the three hand-built `UserNegotiationContext` builders, and the
|
|
888
|
+
`negotiate_existing` operation mode are all deleted.
|
|
889
|
+
- **In-flight negotiations from before this release are not migrated.** The
|
|
890
|
+
negotiation task's shape changed (per-negotiation conversation, dedicated
|
|
891
|
+
`brief` column, new `metadata` shape); old rows are orphaned, not read by
|
|
892
|
+
the new graph.
|
|
893
|
+
|
|
894
|
+
## 28.1.0 - 2026-08-23
|
|
895
|
+
|
|
896
|
+
### Changed
|
|
897
|
+
|
|
898
|
+
- **A pre-contact consult that comes back `ok` now decides the opening
|
|
899
|
+
instead of merely offering the agent another draft.** Previously, once the
|
|
900
|
+
client answered the one question the initiator paused to ask, the resumed
|
|
901
|
+
turn-0 decision was entirely re-drafted: an agent that still held a
|
|
902
|
+
withdraw-worthy concern it never asked the client about (e.g. a location
|
|
903
|
+
preference read from the profile rather than the signal) could withdraw
|
|
904
|
+
anyway, seconds after the client answered the thing it did ask, with the
|
|
905
|
+
counterparty never contacted. Now, if the resumed turn drafts `withdraw`
|
|
906
|
+
and the dimension actually asked about reconciled to `ok`, the graph
|
|
907
|
+
RE-ISSUES the turn once — a fresh model call, explicitly told the answer
|
|
908
|
+
settled the thing it asked and that withdrawing on an unasked concern is
|
|
909
|
+
not available now — and runs the result through every gate the first draft
|
|
910
|
+
faced, rather than rebinding the withdraw's own action: a rebind would have
|
|
911
|
+
shipped that draft's message and reasoning (written to argue against the
|
|
912
|
+
match) verbatim as the opening, both to the counterparty's agent and in the
|
|
913
|
+
web transcript. An unasked concern belongs in the exchange with the
|
|
914
|
+
counterparty's agent, not in a quiet screen-out the client was never asked
|
|
915
|
+
to weigh in on. A `conflict` or still-`unknown` answer leaves the withdraw
|
|
916
|
+
standing, unchanged; a re-issue that withdraws again lands on the same
|
|
917
|
+
quiet `screened_out` outcome.
|
|
918
|
+
|
|
919
|
+
## 28.0.0 - 2026-08-22
|
|
920
|
+
|
|
921
|
+
### Removed
|
|
922
|
+
|
|
923
|
+
- **BREAKING: background enrichment and `user_contexts` are gone; profile
|
|
924
|
+
saves decompose straight into premises.** `EnrichmentRunInput`,
|
|
925
|
+
`EnrichmentRunRecord`, and `UserContextGenerator` are off the barrel — the
|
|
926
|
+
enrichment MCP tools are prefill-only (`research_profile`) now, and
|
|
927
|
+
identity mutation happens through profile saves and REST onboarding
|
|
928
|
+
endpoints, not agent-driven `create_user_context`/`confirm_user_context`.
|
|
929
|
+
- **BREAKING: `EnrichmentGraphFactory` is query-only.** `write`/`generate`
|
|
930
|
+
operation modes, `decompose_premises`, scraping, and Chat-API
|
|
931
|
+
auto-enrichment are gone from the graph — it now only answers "does this
|
|
932
|
+
user have an enriched profile" (`operationMode: 'query'`). The constructor
|
|
933
|
+
narrows to `(database)`; `scraper`, `enricher`, and `premiseGraph` are no
|
|
934
|
+
longer accepted. `EnrichmentGraphDatabase` narrows to
|
|
935
|
+
`getProfile | getProfileByUserId | getPremisesForUser`.
|
|
936
|
+
|
|
937
|
+
### Added
|
|
938
|
+
|
|
939
|
+
- **`PremiseGraphFactory` gains a `decompose` operation mode**: given
|
|
940
|
+
`{ userId, input }` (free text — chat, bio, or profile fields), it
|
|
941
|
+
extracts individual premises via `PremiseDecomposer`, applies any
|
|
942
|
+
retractions and bio revision the decomposer detects, and creates each
|
|
943
|
+
premise through the normal create pipeline (analyze → embed → dedupe →
|
|
944
|
+
persist → index). This replaces the removed enrichment-graph write path as
|
|
945
|
+
the one way host code turns free text into premises.
|
|
946
|
+
`PremiseGraphDatabase` gains `getUser` and `updateUser`.
|
|
947
|
+
|
|
948
|
+
## 27.0.0 - 2026-08-22
|
|
949
|
+
|
|
950
|
+
### Changed
|
|
951
|
+
|
|
952
|
+
- **Discovery evaluates its whole candidate pool and surfaces at least 10
|
|
953
|
+
matches when the pool allows it.** Retrieval limits were raised
|
|
954
|
+
(`LIMIT_PER_STRATEGY` 30→80, `PER_INDEX_LIMIT` 80→160) and the intent path
|
|
955
|
+
re-runs its search with no similarity floor once when the deduped pool has
|
|
956
|
+
fewer than `DISCOVERY_MIN_MATCHES` (10) distinct users. Evaluation now
|
|
957
|
+
scores the entire pool (capped at 80 by rank) in one parallel round instead
|
|
958
|
+
of batching 25 at a time with an early stop on the first passing batch —
|
|
959
|
+
pass rate does not track similarity rank, so batching was stranding real
|
|
960
|
+
matches behind an over-scored head cluster. Every passing candidate is
|
|
961
|
+
returned uncapped; when fewer than 10 pass, the run fills the rest with the
|
|
962
|
+
best-scored rejected candidates (tiebroken by similarity), persisted with
|
|
963
|
+
their real score. `rankingNode` no longer defaults to a 20-item limit —
|
|
964
|
+
only a caller-supplied `options.limit` cuts the list now.
|
|
965
|
+
- `not_accepted` evaluator verdicts now carry the model's actors under
|
|
966
|
+
`returnAll` (previously always `[]`) so a rejected candidate can be used as
|
|
967
|
+
a fill; guard drops (`incomplete_actors`, `unsupported_claim`) still carry
|
|
968
|
+
none and are never fills.
|
|
969
|
+
|
|
970
|
+
### Removed
|
|
971
|
+
|
|
972
|
+
- **BREAKING: the `continue_discovery` operation mode is gone**, along with
|
|
973
|
+
the batched-evaluation continuation it existed for: `remainingCandidates`
|
|
974
|
+
(state field and graph output), the `evaluation_bound` trace entry, and
|
|
975
|
+
`'evaluation_bound_reached'` / `unevaluatedCandidates` on
|
|
976
|
+
`OpportunityDiscoverySummary`. Evaluation no longer batches or stops early,
|
|
977
|
+
so there is nothing left to page into.
|
|
978
|
+
|
|
979
|
+
## 26.0.0 - 2026-08-22
|
|
980
|
+
|
|
981
|
+
### Changed
|
|
982
|
+
|
|
983
|
+
- **BREAKING: the intent graph routes on the shape of its input, not an
|
|
984
|
+
`operationMode` flag.** `operationMode` is gone from the graph's invoke
|
|
985
|
+
input. Callers now signal intent by which fields they set:
|
|
986
|
+
`inputContent` alone creates; `inputContent` + `targetIntentIds` is an
|
|
987
|
+
explicit update; `targetIntentIds` + `archive: true` expires; `targetIntentIds`
|
|
988
|
+
+ `status` pauses/resumes; `proposalId` (+ `description`, `networkId`)
|
|
989
|
+
confirms a stored proposal; none of the above reads. `dryRun: true` replaces
|
|
990
|
+
the old `propose` mode. `targetIntentIds` alone, or more than one of
|
|
991
|
+
{content, archive, status, proposalId} set at once, is now a graph-level
|
|
992
|
+
input error rather than a silent no-op or an implicit default.
|
|
993
|
+
- **BREAKING: `IntentGraphDatabase` gained required members.** Archive now
|
|
994
|
+
performs its full cleanup (network-association removal, referencing
|
|
995
|
+
opportunity expiry) itself, and the graph owns pause/resume and
|
|
996
|
+
proposal-confirmation persistence. Hosts implementing this interface must
|
|
997
|
+
add `deleteIntentIndexAssociations`, `expireOpportunitiesByIntentActor`,
|
|
998
|
+
`transitionIntentLifecycle`, `compensateFailedResume`, `getProposalForOwner`,
|
|
999
|
+
`revisePendingProposal`, and `confirmProposalIntent`.
|
|
1000
|
+
- **BREAKING: `IntentGraphQueue` gained `addResumeDiscoveryJob`.** The graph
|
|
1001
|
+
enqueues resume discovery directly (and compensates back to `PAUSED` on a
|
|
1002
|
+
failed enqueue) instead of leaving that to a host-side event hook.
|
|
1003
|
+
|
|
1004
|
+
### Added
|
|
1005
|
+
|
|
1006
|
+
- `IntentLifecycleStatus`, `TransitionLifecycleResult`, `IntentProposalRecord`,
|
|
1007
|
+
`ReviseIntentProposalInput`, and `ConfirmProposalResult` are now exported
|
|
1008
|
+
from the package barrel.
|
|
1009
|
+
|
|
1010
|
+
### Removed
|
|
1011
|
+
|
|
1012
|
+
- The inferrer's profile-fallback path (`allowProfileFallback`, content-less
|
|
1013
|
+
inference) had no live caller and is gone along with the `delete` operation
|
|
1014
|
+
mode it was keyed on.
|
|
1015
|
+
|
|
1016
|
+
## 25.0.0 - 2026-08-21
|
|
1017
|
+
|
|
1018
|
+
### Removed
|
|
1019
|
+
|
|
1020
|
+
- **BREAKING: principal reachability no longer gates consultation.** A seat's
|
|
1021
|
+
agent may always `ask_user` its own client; whether anyone is behind the
|
|
1022
|
+
account is not the author's concern. Gone: `UserNegotiationContext.principalUnreachable`,
|
|
1023
|
+
the optional `isPrincipalUnreachable` host port on `NegotiationGraphDatabase`,
|
|
1024
|
+
the `principal_unreachable` ask-inadmissibility reason, the
|
|
1025
|
+
`PRINCIPAL_UNREACHABLE_*` prompt rules, the init-node stamp and the
|
|
1026
|
+
detail-reader / `get_negotiation` live re-stamp. Seed personas (`.test`
|
|
1027
|
+
mailboxes) negotiate exactly like real users now — in the sandbox four of
|
|
1028
|
+
five personas had been silenced by construction, and the question flow
|
|
1029
|
+
could not be observed for them.
|
|
1030
|
+
|
|
1031
|
+
## 24.0.0 - 2026-08-21
|
|
1032
|
+
|
|
1033
|
+
### Removed
|
|
1034
|
+
|
|
1035
|
+
- **BREAKING: every environment feature gate is gone, and what each environment
|
|
1036
|
+
was running became the code's behaviour.** No accessor in this package reads
|
|
1037
|
+
`process.env` for a behaviour decision any more; configuration narrows to
|
|
1038
|
+
credentials, endpoints, and the model/log values the host supplies.
|
|
1039
|
+
|
|
1040
|
+
Off the barrel: `configuredAskUserEnabled`, `askUserAnswerWindowMs`,
|
|
1041
|
+
`discoveryEvaluatorMinScore`, `negotiationConsultationPolicyMode`,
|
|
1042
|
+
`negotiationEvidenceQuestionsMode`, `poolQuestionsRanking`,
|
|
1043
|
+
`poolQuestionsMiningMode`, `poolQuestionsMode`, `poolQuestionsPushMode`,
|
|
1044
|
+
`poolQuestionsStampNewborn`, `poolQuestionsVisitTrigger`,
|
|
1045
|
+
`POOL_VISIT_MINING_DEBOUNCE_MS`, `isIntroducerDiscoveryEnabled`,
|
|
1046
|
+
`runIntroducerDiscovery`, `selectContactsForDiscovery`,
|
|
1047
|
+
`shouldRunIntroducerDiscovery`, `IntroducerDiscoveryDatabase`,
|
|
1048
|
+
`IntroducerDiscoveryQueue`, `INTRODUCER_DISCOVERY_SOURCE`,
|
|
1049
|
+
`ContactWithIntents`, `MAX_CONTACTS_PER_CYCLE`, `MAX_CANDIDATES_PER_CONTACT`.
|
|
1050
|
+
The five `poolQuestions*` accessors had no callers at all — they read
|
|
1051
|
+
variables retired with the card question generators.
|
|
1052
|
+
|
|
1053
|
+
Behaviour now fixed in code: negotiations stamp protocol `v2`; `ask_user` and
|
|
1054
|
+
the deterministic consultation policy are on; deadlock-shift is on; the
|
|
1055
|
+
negotiator drafts in the `skeptic` stance (`advocate` and `evaluator`, and the
|
|
1056
|
+
`stance*` predicates that distinguished them, are gone); negotiators receive
|
|
1057
|
+
only each participant's exact opportunity-bound signal; HyDE generates under
|
|
1058
|
+
`frame-v1`; candidate evaluation runs in parallel; retrieval floor is `0.20`
|
|
1059
|
+
and the evaluator score floor is `40`; the two question miners are pinned to
|
|
1060
|
+
`shadow`.
|
|
1061
|
+
|
|
1062
|
+
- **BREAKING: profile matching is removed — discovery is intent-to-intent only.**
|
|
1063
|
+
Premise-to-premise, context-to-context and context-to-intent strategies are
|
|
1064
|
+
gone, along with the `profileCorpus` hint on the embedder interface. Premises
|
|
1065
|
+
remain as an entity; they are no longer a matching corpus.
|
|
1066
|
+
|
|
1067
|
+
- **BREAKING: introducer discovery is removed** — the queue, the maintenance-graph
|
|
1068
|
+
node, and the on-behalf-of persistence path (`onBehalfOfUserId` is off the
|
|
1069
|
+
opportunity graph state; nothing assigned it once the queue was gone). The
|
|
1070
|
+
`introducer_discovery` opportunity source value is kept as read-only history:
|
|
1071
|
+
nothing stamps it, and rows created before this release still carry it.
|
|
1072
|
+
|
|
1073
|
+
- **BREAKING: the negotiation outreach screen gate is gone.** `NegotiationScreener`
|
|
1074
|
+
is off the barrel, and the graph is now `init → turn* → finalize` — every
|
|
1075
|
+
negotiation that reaches `init` proceeds to its first turn. The gate was one
|
|
1076
|
+
structured LLM call before the first turn that could return `pass` and end the
|
|
1077
|
+
negotiation as `screened_out` with the counterparty never contacted.
|
|
1078
|
+
|
|
1079
|
+
It was removed because questions come from parked negotiations: a negotiation
|
|
1080
|
+
screened out never runs a turn, so it never stalls, never parks, and can never
|
|
1081
|
+
produce a user-facing question. The gate silently removed matches from the one
|
|
1082
|
+
pipeline that generates them.
|
|
1083
|
+
|
|
1084
|
+
Also gone: `negotiation.graph.screen.ts` and `negotiation.screen.contracts.ts`
|
|
1085
|
+
in full (`NEGOTIATION_SCREEN_MODES`, `NegotiationScreenMode`, `SCREEN_MODE`,
|
|
1086
|
+
`ScreenDecisionSchema`, `ScreenDecision`, `ScreenDecisionRecord`,
|
|
1087
|
+
`blocksNegotiationBeforeFirstTurn`), the `screener` dep on
|
|
1088
|
+
`NegotiationGraphDeps`, the `screenDecision` graph-state field, the
|
|
1089
|
+
`routeAfterScreen` edge, the optional `setTaskScreenDecision` port method on
|
|
1090
|
+
`NegotiationGraphDatabase`, the `negotiationScreener` model-config entry, and
|
|
1091
|
+
the `screenedOut` field of `ConsultationEligibilityInput` (always false with
|
|
1092
|
+
no gate to set it). `NegotiatorMemoryScope` narrows to `"turn"`, and
|
|
1093
|
+
`renderNegotiatorMemorySection` loses its options argument — the
|
|
1094
|
+
`memoryHintsInstruction` it carried existed only for the screen prompt.
|
|
1095
|
+
|
|
1096
|
+
### Changed
|
|
1097
|
+
|
|
1098
|
+
- **`negotiationHasMadeContact` moved to `negotiation.protocol.ts`.** Not a
|
|
1099
|
+
screening helper: finalize and the turn node both call it for live turn logic
|
|
1100
|
+
(the IND-564 opening-`withdraw` guard, and the `screened_out` label). It lived
|
|
1101
|
+
in the screen module by accident of history. Package-internal, so no consumer
|
|
1102
|
+
import changes.
|
|
1103
|
+
|
|
1104
|
+
- **`screened_out` now has exactly one live writer** — the IND-564 opening-turn
|
|
1105
|
+
`withdraw` guard, where the acting agent refuses before anything is sent.
|
|
1106
|
+
`outcome.reasoning` for such a run is unconditionally the withdrawing turn's
|
|
1107
|
+
reasoning; there is no screen record left to prefer over it.
|
|
1108
|
+
|
|
1109
|
+
### Read-only history (deliberately kept)
|
|
1110
|
+
|
|
1111
|
+
- The `screened_out` outcome reason, `tasks.metadata.screenDecision`, and the
|
|
1112
|
+
owner-only `screenDecision` API projection. Nothing writes the metadata key
|
|
1113
|
+
any more, but negotiations that ran before this release still carry one and
|
|
1114
|
+
must still render for their initiator. Each survivor is marked as such at its
|
|
1115
|
+
definition.
|
|
1116
|
+
|
|
1117
|
+
## 23.6.4 - 2026-08-21
|
|
1118
|
+
|
|
1119
|
+
### Added
|
|
1120
|
+
|
|
1121
|
+
- **`buildAgentSelfIntroduction` is now actually exported.** 23.6.3's entry
|
|
1122
|
+
named it as part of the new surface, but it was only reachable from inside
|
|
1123
|
+
the package — the three chat personas import it directly. It is now on the
|
|
1124
|
+
barrel (`buildAgentSelfIntroduction`, `AgentIdentityOptions`), which is what
|
|
1125
|
+
makes that claim true for consumers.
|
|
1126
|
+
|
|
1127
|
+
### Changed
|
|
1128
|
+
|
|
1129
|
+
- **`buildAgentSelfIntroduction`'s `userName` is optional.** Additive: every
|
|
1130
|
+
existing caller passes it and gets the same sentence. Absent, the builder
|
|
1131
|
+
emits `You are <name>, <role>.` or, with no name either, `You are <role>.` —
|
|
1132
|
+
the form a surface needs when its role phrase already says whose agent this
|
|
1133
|
+
is and it never resolves a client display name. The API's IntentAgent loop
|
|
1134
|
+
is the first such caller.
|
|
1135
|
+
|
|
1136
|
+
## 23.6.3 - 2026-08-21
|
|
1137
|
+
|
|
1138
|
+
### Added
|
|
1139
|
+
|
|
1140
|
+
- **Persona identity + create_intent scope rule (#1479) — the version stamp
|
|
1141
|
+
the change shipped without.** Every chat persona now introduces itself as
|
|
1142
|
+
the user's own agent: `buildAgentSelfIntroduction`, plus
|
|
1143
|
+
`createSignalPersona` / `createOnboardingPersona` factories taking
|
|
1144
|
+
`agentName` the way the negotiator already did. Tool registration gained
|
|
1145
|
+
the scope rule (`isToolAllowedInScope`, `filterToolsForScope`). #1479
|
|
1146
|
+
merged these exports without bumping, so two different export surfaces
|
|
1147
|
+
briefly answered to 23.6.2 on the `rc` tag — this entry gives the new
|
|
1148
|
+
surface its own version.
|
|
1149
|
+
|
|
1150
|
+
## 23.6.2 - 2026-08-21
|
|
1151
|
+
|
|
1152
|
+
### Fixed
|
|
1153
|
+
|
|
1154
|
+
- **A premise-matched counterparty is premise-bound — two wrongs stopped
|
|
1155
|
+
agreeing.** A premise-matched opportunity actor carries BOTH keys: `premise`
|
|
1156
|
+
is its own fact, `intent` names the intent it matched AGAINST — the
|
|
1157
|
+
recipient's. Two sites independently preferred `intent` whenever the key
|
|
1158
|
+
existed, and their mistakes agreed with each other: the api's ask-user
|
|
1159
|
+
capture stamped every premise-matched park's `counterpartyBinding` with the
|
|
1160
|
+
recipient's own intent (so the claim's counterparty-liveness check could
|
|
1161
|
+
never pass — observed live as `admission:"invalid"` after #1474/#1475 had
|
|
1162
|
+
already made settle and claim drift-tolerant), and this package's
|
|
1163
|
+
`resolveOpportunityActorBinding` resolved a dual-key actor to that same
|
|
1164
|
+
wrong intent binding — so the re-drive's continuation revalidation
|
|
1165
|
+
(`opportunityActorMatchesBinding` in `negotiateExistingOpportunity`) would
|
|
1166
|
+
have accepted the mis-stamp and refused a corrected premise stamp as
|
|
1167
|
+
`stale_continuation`, one gate after the claim.
|
|
1168
|
+
|
|
1169
|
+
Both flips ship together, mirror-identical: a present `premise` is the
|
|
1170
|
+
binding, `intent` binds only in its absence. Mirror consequence, intended:
|
|
1171
|
+
a dual-key actor no longer matches an intent-kind binding naming its
|
|
1172
|
+
matched-against intent — the gate stops accepting mis-stamped settlements,
|
|
1173
|
+
which already fail the claim's liveness check earlier, so nothing that
|
|
1174
|
+
works today breaks.
|
|
1175
|
+
|
|
1176
|
+
## 23.6.1 - 2026-08-20
|
|
1177
|
+
|
|
1178
|
+
### Fixed
|
|
1179
|
+
|
|
1180
|
+
- **An answer beats staleness — drift is logged, never fatal.** Observed live:
|
|
1181
|
+
a client answered her own parked question ("Timing: This week") through the
|
|
1182
|
+
new MCP answer lane, routing succeeded, consumption ran — and the settle
|
|
1183
|
+
returned `lost`, because the signal had been edited twice since the park and
|
|
1184
|
+
the revalidation fence required the world to look exactly as it did at park
|
|
1185
|
+
time. The park became a zombie: still `input_required`, still rendered as
|
|
1186
|
+
"waiting on YOUR answer" by every surface, structurally unanswerable. The
|
|
1187
|
+
design law is explicit: signal edits cascade nothing, and a stale negotiation
|
|
1188
|
+
is solved by ANSWERING its question — the user's answer is the freshest
|
|
1189
|
+
commitment there is, and the resumed turn rebuilds its context from current
|
|
1190
|
+
data anyway.
|
|
1191
|
+
|
|
1192
|
+
The settle's one fence is now two. Coherence stays hard: an answer that does
|
|
1193
|
+
not belong to its park (settlement mismatch, wrong recipient, task no longer
|
|
1194
|
+
parked, a dismiss/timeout settlement won the race) is still refused. Drift
|
|
1195
|
+
stops losing: within a live opportunity and an active signal, the answer
|
|
1196
|
+
settles and resumes regardless of what moved since the park.
|
|
1197
|
+
|
|
1198
|
+
- **The unresumable tail is an explicit proposal, not a silent drop.** When
|
|
1199
|
+
current reality genuinely cannot continue — terminal opportunity or archived
|
|
1200
|
+
signal — the answer is still recorded as heard: settlement result and resume
|
|
1201
|
+
outcome `recorded_unresumable` (additive), the block-consumption result
|
|
1202
|
+
counts it in its own `recorded` array so a `skipped` count can never again
|
|
1203
|
+
hide it, and the implementation retires the park and tells the client the
|
|
1204
|
+
truth, proposing re-discovery under the updated signal — an offer, never an
|
|
1205
|
+
automatic act.
|
|
1206
|
+
|
|
1207
|
+
## 23.6.0 - 2026-08-20
|
|
1208
|
+
|
|
1209
|
+
### Added
|
|
1210
|
+
|
|
1211
|
+
- **The MCP surface can now ACT on the question flow, not just see it.** Since
|
|
1212
|
+
23.5.1 `list_negotiations` says the park — "open question 3, 'Timing'" — to
|
|
1213
|
+
an external client that had no tool to answer it: the answer lane was the
|
|
1214
|
+
negotiator persona's chat-only appended tool, and the owner's verdict levers
|
|
1215
|
+
did not exist on MCP at all. Three tools close the read-and-act gap, all
|
|
1216
|
+
registered on the MCP tool registry surface only:
|
|
1217
|
+
|
|
1218
|
+
- `answer_pending_question(negotiationId, question, answer)` routes the
|
|
1219
|
+
principal's answer to the open question a parked negotiation is waiting on,
|
|
1220
|
+
over the EXISTING `NegotiatorAnswerToolsHost` — the same
|
|
1221
|
+
`readOpenQuestionsForIntent` numbering, the same serialized consumption
|
|
1222
|
+
queue, the same #1432 resume spine. MCP has no pinned intent, so the tool
|
|
1223
|
+
resolves scope from the negotiation the client is looking at: the id the
|
|
1224
|
+
park annotation sits on → the caller's own actor intent on that pairing →
|
|
1225
|
+
the host. The `question` number passes through untouched; it and the park
|
|
1226
|
+
annotation come from one enumeration and cannot drift (the #1470 rule).
|
|
1227
|
+
- `reject_opportunity` / `accept_opportunity` (intentId, numbered
|
|
1228
|
+
counterparty, optional reason in the owner's own words) reuse the
|
|
1229
|
+
negotiator verdict host verbatim — the same Radar Skip/Start-Chat service
|
|
1230
|
+
call, outcome hooks and question retirement in its wake, positions never
|
|
1231
|
+
ids. Capability access is `human_only`: exactly the session-authenticated
|
|
1232
|
+
class the IND-593 owner-provenance binding admits, and the handler
|
|
1233
|
+
re-checks the host-bound provenance so an API-key agent is refused even if
|
|
1234
|
+
the tool were ever mis-listed. Hermes negotiator credentials fail closed as
|
|
1235
|
+
unclassified for all three tools.
|
|
1236
|
+
|
|
1237
|
+
- **`get_negotiation` says the park** — the #1472 incident, one level down: it
|
|
1238
|
+
is the tool the poller prompt says to call FIRST, and on a parked negotiation
|
|
1239
|
+
it narrated a lifecycle built without the park. The detail reader now runs
|
|
1240
|
+
the same canonical park predicate the listing runs (`classifyInflightPark` /
|
|
1241
|
+
`classifyPostStallPark`) over the task and messages it already holds, names
|
|
1242
|
+
the open question through the same shared host record, projects the park
|
|
1243
|
+
top-level and into `lifecycle` (superseding the status label), and — for an
|
|
1244
|
+
external seat that could not see dimensions or `settles` — projects the
|
|
1245
|
+
persisted `askUser` and `checklist` payloads on turns that carry them.
|
|
1246
|
+
Non-parked negotiations render byte-for-byte as before.
|
|
1247
|
+
|
|
1248
|
+
- **`get_negotiation` re-stamps principal reachability from the live read.**
|
|
1249
|
+
The persisted `turnContext` is a park-time snapshot; `ownUser.principalUnreachable`
|
|
1250
|
+
is now corrected in both directions through the host's
|
|
1251
|
+
`isPrincipalUnreachable` port — the same re-stamp REST pickup applies — so an
|
|
1252
|
+
external seat is never told it can consult a principal nobody is behind, or
|
|
1253
|
+
the reverse.
|
|
1254
|
+
|
|
1255
|
+
- **`list_negotiations` can filter for the parked state.** The `status` filter
|
|
1256
|
+
gains `input_required`; `active` and `all` behave exactly as before. A
|
|
1257
|
+
post-stall park lives on a `completed` negotiation and is documented as such
|
|
1258
|
+
rather than smuggled into the status filter.
|
|
1259
|
+
|
|
1260
|
+
### Fixed
|
|
1261
|
+
|
|
1262
|
+
- **`read_activity_summary` stops counting questions from the retired card
|
|
1263
|
+
table.** Pending question counts now come from the parked negotiations —
|
|
1264
|
+
a mid-flight `input_required` consult naming the owner as recipient, or a
|
|
1265
|
+
post-stall park trailing the authored gap — keyed by the same
|
|
1266
|
+
`negotiation_inflight`/`negotiation` modes the projection already maps to the
|
|
1267
|
+
negotiations domain, so permission inheritance is unchanged. Leftover
|
|
1268
|
+
pending rows in the retired `questions` table contribute nothing; answered
|
|
1269
|
+
history still reads the table, where it legitimately lives.
|
|
1270
|
+
|
|
1271
|
+
- **Honest words where external clients read them.** The negotiations guidance
|
|
1272
|
+
topic, the workflows topic, and `MCP_INSTRUCTIONS` now carry the park stage —
|
|
1273
|
+
what a park is, what the `park` fields mean, and that answering is the only
|
|
1274
|
+
thing that resumes a parked negotiation. The three negotiation tool
|
|
1275
|
+
descriptions state plainly that turns submitted through external surfaces are
|
|
1276
|
+
NOT run through the conclusion floor, decline law, or copy-loop guard: until
|
|
1277
|
+
external write parity ships, the docs must not imply otherwise.
|
|
1278
|
+
|
|
1279
|
+
## 23.5.1 - 2026-08-20
|
|
1280
|
+
|
|
1281
|
+
### Fixed
|
|
1282
|
+
|
|
1283
|
+
- **The negotiation listing says the park, from the same record every other
|
|
1284
|
+
answerability surface reads.** Observed live: a client asked her agent "do we
|
|
1285
|
+
have a question?" while a negotiation had sat parked `input_required` on her
|
|
1286
|
+
side for two hours with the open question "Timing: This week". Every 23.5.0
|
|
1287
|
+
surface was correct — the precedence gate found the question, and the
|
|
1288
|
+
prompt's open-questions section named it at position 1. Then the model called
|
|
1289
|
+
`list_negotiations`, which renders lifecycle from OPPORTUNITY STATUS, where
|
|
1290
|
+
the pairing legitimately reads `negotiating`, and which said nothing at all
|
|
1291
|
+
about the park. Holding a static context line saying one thing and a
|
|
1292
|
+
just-executed tool result saying another, it went with the tool: "there are
|
|
1293
|
+
currently no open questions… I am still negotiating with the other agent…
|
|
1294
|
+
nothing for you to decide." Both clauses false at the task level; both
|
|
1295
|
+
faithful to what the tool rendered.
|
|
1296
|
+
|
|
1297
|
+
The listing was the last surface still deriving "what is happening" from a
|
|
1298
|
+
source other than the shared resolver, so the tool and the context could
|
|
1299
|
+
disagree — and the tool wins the model's trust every time. It now carries a
|
|
1300
|
+
`park` on any negotiation that holds one: `waitingOn: "you" | "counterparty"`,
|
|
1301
|
+
and for a park on the client's own side the open question's number and label.
|
|
1302
|
+
|
|
1303
|
+
- **One call, every surface — the answer-openness rule extended to its last
|
|
1304
|
+
holdout.** The question's NUMBER and LABEL come from
|
|
1305
|
+
`NegotiationListingParkHost`, whose host implementation resolves them through
|
|
1306
|
+
the same call the open-questions prompt section and `answer_pending_question`
|
|
1307
|
+
make. The listing does not enumerate anything of its own, so the number the
|
|
1308
|
+
client is shown is the number that routes their answer. A question's
|
|
1309
|
+
`alsoUnblocks` refs carry that same number, since one answer resumes them all.
|
|
1310
|
+
|
|
1311
|
+
- **Whose side a park is on is the canonical predicate, not a second one.**
|
|
1312
|
+
`classifyParkedNegotiation` is split into `classifyInflightPark` and
|
|
1313
|
+
`classifyPostStallPark`, pure over the task and messages a caller already
|
|
1314
|
+
holds; the async function is now the reading half around them and keeps its
|
|
1315
|
+
lazy messages read. The listing calls them with material it already loaded, so
|
|
1316
|
+
park classification costs no extra query and cannot drift from the predicate
|
|
1317
|
+
answer routing uses. Parked-ness is never re-derived from opportunity status.
|
|
1318
|
+
|
|
1319
|
+
- **A park on the counterparty is narrated, never quoted.** It renders as
|
|
1320
|
+
waiting on their side with no question content: that question is not this
|
|
1321
|
+
client's to read.
|
|
1322
|
+
|
|
1323
|
+
### Changed
|
|
1324
|
+
|
|
1325
|
+
- **`lifecycleLabel` states the park, superseding the status label.** The
|
|
1326
|
+
persona is told to take `lifecycleLabel` as its user-facing wording, and "the
|
|
1327
|
+
agents are still negotiating" is exactly the sentence that became a false
|
|
1328
|
+
"nothing for you to decide". `opportunityStatus` still reports the true
|
|
1329
|
+
status; what it may no longer do is supply the sentence.
|
|
1330
|
+
`connectionState` gains `parked_awaiting_your_answer` and
|
|
1331
|
+
`parked_awaiting_counterparty`, and `buildLifecycleNarration` takes an
|
|
1332
|
+
optional third argument. A negotiation with no park renders byte-for-byte as
|
|
1333
|
+
it did in 23.5.0, and is pinned by a fixture spec.
|
|
1334
|
+
|
|
1335
|
+
- **The tool description and the negotiator prompt both say the two agree.**
|
|
1336
|
+
`list_negotiations` documents `input_required` as a status, documents `park`,
|
|
1337
|
+
and states that the numbers come from the same record the open-questions
|
|
1338
|
+
context section does — so the model has no basis to rank one over the other.
|
|
1339
|
+
It also states that `negotiating` alone never means "nothing is waiting on
|
|
1340
|
+
you". The persona gains one grounding rule saying the same thing.
|
|
1341
|
+
`NegotiationListingParkHost` is optional: without it the listing still says
|
|
1342
|
+
whether a pairing is parked and on whose side, it just cannot name the
|
|
1343
|
+
question's number.
|
|
1344
|
+
|
|
1345
|
+
## 23.5.0 - 2026-08-20
|
|
1346
|
+
|
|
1347
|
+
### Added
|
|
1348
|
+
|
|
1349
|
+
- **The owner's verdict has a lane in their own DM.** Observed live: in the
|
|
1350
|
+
negotiator DM for one signal, a client told their agent to reject the
|
|
1351
|
+
counterparty — a pairing parked `input_required`. The agent could not comply.
|
|
1352
|
+
The owner makes exactly three kinds of decision in that room. They ANSWER a
|
|
1353
|
+
question a parked negotiation asked, which `answer_pending_question` gave a
|
|
1354
|
+
lane. They EDIT the signal, which `update_intent` always covered.
|
|
1355
|
+
And they pass a VERDICT on a counterparty, which had no lever at all. So on
|
|
1356
|
+
"reject them" the persona's whole repertoire was to say something back, or to
|
|
1357
|
+
edit the signal instead; the pairing stayed parked and the counterparty
|
|
1358
|
+
stayed live.
|
|
1359
|
+
|
|
1360
|
+
`update_opportunity` is in the negotiator toolset and cannot substitute for
|
|
1361
|
+
either half of this. `admitOpportunityUpdate` blocks a `negotiating` pairing
|
|
1362
|
+
outright, and the IND-593 owner-approval boundary fails closed on the chat
|
|
1363
|
+
surface by design — `createChatTools` binds
|
|
1364
|
+
`{ surface: 'chat', sessionAuthenticated: false }`, and a mediated surface is
|
|
1365
|
+
denied `untrusted_provenance`. The verdict levers that exist are the Radar
|
|
1366
|
+
card's Skip and Start-Chat and the REST endpoints behind them, none of which
|
|
1367
|
+
the client's own agent can reach.
|
|
1368
|
+
|
|
1369
|
+
So `createNegotiatorVerdictTools` adds `reject_opportunity` and
|
|
1370
|
+
`accept_opportunity` to the negotiator persona, on the same pattern
|
|
1371
|
+
`answer_pending_question` set. Appended AFTER the allowlist filter and only in
|
|
1372
|
+
an intent-pinned session with `negotiatorVerdictTools` injected, so they never
|
|
1373
|
+
enter the shared chat-tool registry and the orchestrator and MCP tool listing
|
|
1374
|
+
cannot see them. `NegotiatorVerdictToolsHost` is the whole surface the package
|
|
1375
|
+
knows; the composition root owns everything behind it.
|
|
1376
|
+
|
|
1377
|
+
- **Numbered refs, never ids.** The prompt renders this signal's actionable
|
|
1378
|
+
counterparties as `N. {name} — {state}`, and the tool takes the number. The
|
|
1379
|
+
schema offers no place to put an id and no result string carries one. The rule
|
|
1380
|
+
is `answer_pending_question`'s, for a sharper reason: a ref the model can name
|
|
1381
|
+
is a ref it can get wrong, and a wrong ref here declines the wrong person.
|
|
1382
|
+
The host owns the mapping, and a successful result names WHO the write landed
|
|
1383
|
+
on — so the confirmation the client reads comes from the write rather than
|
|
1384
|
+
from the model's belief about which counterparty it picked.
|
|
1385
|
+
|
|
1386
|
+
- **An optional `reason`, in the client's own words.** Capped at 500 characters,
|
|
1387
|
+
omitted entirely when they gave none. The tool description and the prompt both
|
|
1388
|
+
say it is never to be inferred or written for them.
|
|
1389
|
+
|
|
1390
|
+
### Changed
|
|
1391
|
+
|
|
1392
|
+
- **The pinned-signal prompt gains a verdict section, and only where the tools
|
|
1393
|
+
exist.** `NegotiatorPromptOptions.actionableCounterparties` renders
|
|
1394
|
+
`## Verdicts {userName} can pass here` plus two tool-reference rows. It says
|
|
1395
|
+
the tool call IS the decision — not the sentence about it, and not an edit of
|
|
1396
|
+
the signal; that a verdict the client did not pass must never be passed for
|
|
1397
|
+
them; that `update_opportunity` is not this lever; and that an accept is one
|
|
1398
|
+
side of two and never a connection. Rendered only in an intent-pinned session
|
|
1399
|
+
with a non-empty list, since that is the only place the tools are registered.
|
|
1400
|
+
Absent or empty leaves the prompt byte-identical to 23.4.0.
|
|
1401
|
+
|
|
1402
|
+
- **Result copy is honest at every status.** `executed` names the counterparty
|
|
1403
|
+
and forbids also editing the signal; `none_actionable` forbids implying a
|
|
1404
|
+
decision was recorded; `unknown_counterparty` states plainly that nothing was
|
|
1405
|
+
decided and re-lists the current set; `already_decided` says whose move it is;
|
|
1406
|
+
`error` forbids describing the pairing as decided. A host that throws is
|
|
1407
|
+
caught and reported as `error` rather than costing the client their turn.
|
|
1408
|
+
|
|
1409
|
+
- **Execution is the path the Radar card already takes, and nothing more.** The
|
|
1410
|
+
host behind the seam runs the SAME owner status update the Skip page calls
|
|
1411
|
+
through `PATCH /opportunities/:id/status`, intent-scoped. No new task-state
|
|
1412
|
+
transition is invented, and the retirement of a dismissed pairing's open
|
|
1413
|
+
question is not re-invoked: `OpportunityEvents.onTransition` already fires the
|
|
1414
|
+
exhaustion evaluator on every committed opportunity status write, owner reject
|
|
1415
|
+
included, so a rejected pairing's question dies with it because that arrow was
|
|
1416
|
+
already there.
|
|
1417
|
+
|
|
1418
|
+
## 23.4.0 - 2026-08-20
|
|
1419
|
+
|
|
1420
|
+
### Added
|
|
1421
|
+
|
|
1422
|
+
- **A checklist dimension now declares whose fact it is, and the floor reads
|
|
1423
|
+
it.** Observed live: turn 2 of a sandbox negotiation, initiator seat, a
|
|
1424
|
+
checklist whose two open dimensions were "Query Match: Generative Story
|
|
1425
|
+
Games" and "Query Match: Live Operations" — both about the COUNTERPARTY's
|
|
1426
|
+
work. The agent drafted `question` to the counterparty's agent, which is the
|
|
1427
|
+
protocol's own prescribed move. The conclusion floor (23.3.0) saw a non-ask
|
|
1428
|
+
turn with an askable unknown standing, took `askableUnknowns[0]`, and coerced
|
|
1429
|
+
the turn into a guaranteed `ask_user` — so the client was asked, in her own
|
|
1430
|
+
DM, whether the other person works on generative story games.
|
|
1431
|
+
|
|
1432
|
+
Nothing was wrong with the floor's logic; the logic simply could not see the
|
|
1433
|
+
distinction. "Askable" was `unknown ∧ unasked ∧ budget ∧ reachable ∧ wiring`,
|
|
1434
|
+
and no term in that conjunction knows WHOSE fact is missing. That judgment
|
|
1435
|
+
lived only in the agent — which is exactly the judgment the guarantee exists
|
|
1436
|
+
to override. Where the first unknown happens to be the client's own the
|
|
1437
|
+
guarantee is right; where it is the counterparty's it converts the agent's
|
|
1438
|
+
correct move into a wrong one.
|
|
1439
|
+
|
|
1440
|
+
So the judgment becomes a declared, mechanical property, following the same
|
|
1441
|
+
pattern answerhood set: made ONCE, at authoring, by the agent writing the
|
|
1442
|
+
checklist, then read mechanically forever. `ChecklistItem` gains
|
|
1443
|
+
`settles: 'client' | 'counterparty' | 'either'`, frozen with the dimension —
|
|
1444
|
+
`reconcileChecklist` copies it through untouched, because it is a judgment
|
|
1445
|
+
about the world rather than about the evidence, and a re-scorable one would
|
|
1446
|
+
be a switch an agent could use to turn the floor off for a dimension it would
|
|
1447
|
+
rather not be asked about.
|
|
1448
|
+
|
|
1449
|
+
### Changed
|
|
1450
|
+
|
|
1451
|
+
- **`askableUnknowns` filters on it, so both halves of the floor do.**
|
|
1452
|
+
`assessConcludeAdmissibility` now admits a verdict whose only open dimensions
|
|
1453
|
+
are the counterparty's to state — those are resolved by dialogue with the
|
|
1454
|
+
other agent, or carried, which is what the verdict law has always said about
|
|
1455
|
+
unknowns — and the part-2 guarantee picks only from what survives the filter.
|
|
1456
|
+
Order within the surviving set is still the checklist's own.
|
|
1457
|
+
- **The five-part ask rule gains the mechanical half of its rule 3.** An
|
|
1458
|
+
agent-drafted ask naming a `settles: 'counterparty'` dimension is refused as
|
|
1459
|
+
`counterparty_authoritative`, with the same honest-refusal logging as its
|
|
1460
|
+
siblings. Rule 3 was prompt-only until now; the incident proves the
|
|
1461
|
+
mechanical half matters in both directions — the same field that stops the
|
|
1462
|
+
floor manufacturing the wrong ask stops an agent drafting it.
|
|
1463
|
+
- **The prompt asks for the field where the model authors, and reads it back on
|
|
1464
|
+
every row.** The authoring instruction and the checklist protocol rule both
|
|
1465
|
+
require `settles` per dimension in the vocabulary they already use ("a thing
|
|
1466
|
+
only your client can answer" / "the counterparty's to state"); the rendered
|
|
1467
|
+
checklist labels each row with it, because the agent re-scoring a frozen
|
|
1468
|
+
checklist did not necessarily author it. The conclude-floor re-issue states
|
|
1469
|
+
that counterparty-settled dimensions are not what it is about.
|
|
1470
|
+
|
|
1471
|
+
### Fixed
|
|
1472
|
+
|
|
1473
|
+
- **The generation seam states the field and repairs it, rather than refusing.**
|
|
1474
|
+
Following 23.3.2's split: `ChecklistDraftGenerationSchema` requires `settles`
|
|
1475
|
+
on every dimension — so it renders inside the emitted JSON schema's `required`
|
|
1476
|
+
list, and a field the model need not produce is one it skips — while a
|
|
1477
|
+
`preprocess` fills a missing or unrecognised value with `either` before the
|
|
1478
|
+
enum ever sees it. A `.catch()` on the field would have read as optional to
|
|
1479
|
+
zod and dropped out of `required`, which is why the repair wraps the object.
|
|
1480
|
+
A refusal here throws inside the structured-output call and takes the whole
|
|
1481
|
+
turn with it.
|
|
1482
|
+
- **Legacy checklists are unchanged.** Persisted turns written before the field
|
|
1483
|
+
existed carry no `settles`, and `normalizeSettles` reads them back as
|
|
1484
|
+
`either` — which stays ASKABLE. The default direction is the whole safety
|
|
1485
|
+
argument: `counterparty` would let one unfilled field silently retire the
|
|
1486
|
+
conclusion floor for a negotiation, so no authoring failure, legacy turn, or
|
|
1487
|
+
repaired value can switch it off wholesale. An unrecognised value on the
|
|
1488
|
+
persisted shape reads back as absent rather than failing the item, because
|
|
1489
|
+
that shape also parses the drafts of externally dispatched agents, which
|
|
1490
|
+
never see the generation schema — a whole re-scored checklist discarded over
|
|
1491
|
+
one misspelled marking is the larger loss.
|
|
1492
|
+
|
|
1493
|
+
## 23.3.2 - 2026-08-20
|
|
1494
|
+
|
|
1495
|
+
### Fixed
|
|
1496
|
+
|
|
1497
|
+
- **A question the model wrote itself must not die at the schema that asked for
|
|
1498
|
+
it.** For the first time, the negotiator drafted its own `ask_user` — 23.3.1's
|
|
1499
|
+
re-issue prompt worked and no floor coercion was needed — and the draft was
|
|
1500
|
+
refused by the very schema it was drafted into, twice over. `guaranteed`, the
|
|
1501
|
+
conclusion floor's own mark, was an optional field on the payload handed to
|
|
1502
|
+
the model; the model filled it with `false`, and `z.literal(true)` rejects
|
|
1503
|
+
`false`. The authored `question.title` carried a silent 12-character cap; the
|
|
1504
|
+
model wrote a real 40-character title. Both refusals throw INSIDE the
|
|
1505
|
+
structured-output call, so the turn failed with nothing persisted, the retry
|
|
1506
|
+
was refused the same way, the ask was coerced to a counter, the dialogue ran
|
|
1507
|
+
to the cap and declined. The question was never delivered.
|
|
1508
|
+
|
|
1509
|
+
Two seams were sharing one declaration, and they have opposite jobs. There
|
|
1510
|
+
are now two. `AskUserGenerationSchema` is what a model is ALLOWED TO SAY: it
|
|
1511
|
+
OMITS `guaranteed` entirely — a field only the graph may write should never
|
|
1512
|
+
be offered to the model, rather than offered and defended against afterwards
|
|
1513
|
+
— and it discards unrecognised keys instead of failing the turn over them,
|
|
1514
|
+
since this parse is what produces the object that gets persisted. The
|
|
1515
|
+
persisted `AskUserPayloadSchema` is unchanged: it keeps `guaranteed` and
|
|
1516
|
+
stays `.strict()`, because the record is where the floor's mark is read back
|
|
1517
|
+
out of and where a stray key would do damage. The turn node still strips an
|
|
1518
|
+
agent-claimed mark — externally dispatched personal agents draft against the
|
|
1519
|
+
permissive shape, not the generation schema — so the floor remains the only
|
|
1520
|
+
writer whichever way a draft arrives.
|
|
1521
|
+
|
|
1522
|
+
Every renderer cap on a question now REPAIRS instead of refusing, which is the
|
|
1523
|
+
protocol's own philosophy (`normalizeChecklistItem` repairs toward `unknown`;
|
|
1524
|
+
the anti-echo guard repairs toward honesty) applied where it was missing: a
|
|
1525
|
+
title, prompt, option label or description that runs long is truncated on a
|
|
1526
|
+
word boundary, and a fifth option is dropped. The emitted JSON schema is
|
|
1527
|
+
unchanged, so the model is still TOLD each cap — repair is only what happens
|
|
1528
|
+
when it ignores one — and the conclusion-floor re-issue now names the title
|
|
1529
|
+
cap where it tells the agent to write the question itself. Where nothing can
|
|
1530
|
+
be honestly repaired (one option is not a choice), the generation schema
|
|
1531
|
+
degrades the authored question to absent and keeps the ask: an ask with no
|
|
1532
|
+
wording falls back to the server template, a path the floor's own guaranteed
|
|
1533
|
+
ask already walks. Losing the wording is a smaller loss than losing the turn.
|
|
1534
|
+
|
|
1535
|
+
## 23.3.1 - 2026-08-20
|
|
1536
|
+
|
|
1537
|
+
### Fixed
|
|
1538
|
+
|
|
1539
|
+
- **A task's FIRST turn can park.** The first `ask_user` this system ever fired —
|
|
1540
|
+
produced by 23.3.0's conclusion floor, on the first turn of a resumed
|
|
1541
|
+
session — died at the park with "Ask-user material binding is no longer
|
|
1542
|
+
valid", and the negotiation stalled. The binding capture locks the task row
|
|
1543
|
+
`state = 'working'` and refuses anything else; the graph announced `working`
|
|
1544
|
+
only at the END of a completed turn, so on a task's first turn the row still
|
|
1545
|
+
held its creation state (`submitted`) and no first-turn park could bind. The
|
|
1546
|
+
turn was already on the record when it threw, which makes the failure
|
|
1547
|
+
unretryable — so the whole opportunity ended as `agent_error`.
|
|
1548
|
+
|
|
1549
|
+
The turn node now announces `working` before the capture rather than only
|
|
1550
|
+
after the turn, carrying the same continuation-execution fence as every other
|
|
1551
|
+
state write. The fence in the adapter is unchanged: `working` is the true
|
|
1552
|
+
precondition for a settlement coordinate, and what was wrong was the
|
|
1553
|
+
sequencing, not the check. The flip sits at the park rather than at the top of
|
|
1554
|
+
the turn deliberately — a task that dies before putting anything on the record
|
|
1555
|
+
stays reclaimable under the watchdog's ten-minute `submitted` rule instead of
|
|
1556
|
+
disappearing under the twelve-hour `working` one — and the end-of-turn flip
|
|
1557
|
+
stays for every path that does not park.
|
|
1558
|
+
|
|
1559
|
+
Latent since the turn-0 pre-contact consult shipped and never once hit,
|
|
1560
|
+
because no first-turn ask was ever drafted; the conclusion floor made them
|
|
1561
|
+
routine, a run-existing continuation's turn 0 being the common case. The
|
|
1562
|
+
twenty-five specs covering this loop all missed it because their database
|
|
1563
|
+
stubs accepted any task state at capture time — the new spec's stub asserts
|
|
1564
|
+
the state exactly as the adapter does, on the agent-drafted ask, the
|
|
1565
|
+
floor-guaranteed one, the pre-contact consult and a later-turn ask alike.
|
|
1566
|
+
|
|
1567
|
+
## 23.3.0 - 2026-08-20
|
|
1568
|
+
|
|
1569
|
+
### Changed
|
|
1570
|
+
|
|
1571
|
+
- **A verdict has a floor under it: an askable unknown outranks a conclusion.**
|
|
1572
|
+
Every stage of the flow — signal, discovery, agents talking, match, meet — was
|
|
1573
|
+
verified working except one arrow: the agent asking its own client something
|
|
1574
|
+
only that client can settle. In a week of live traffic it fired zero times,
|
|
1575
|
+
against 23 policy-recognized consultation moments. The reason is structural
|
|
1576
|
+
rather than a bug: the model always had a cheaper exit than asking — assume the
|
|
1577
|
+
unknown away and accept, put the question to the counterparty who does not hold
|
|
1578
|
+
the answer, or simply conclude — and it took one every time. #1463 closed one
|
|
1579
|
+
of those exits (a decline with no conflict behind it). This closes the rest.
|
|
1580
|
+
|
|
1581
|
+
`assessConcludeAdmissibility` makes a drafted TERMINAL verdict — `accept`,
|
|
1582
|
+
`decline`, `reject`, and the initiator's `withdraw` — inadmissible while the
|
|
1583
|
+
checklist holds a dimension scored `unknown` that this principal could still be
|
|
1584
|
+
asked about, reported as `unknowns_askable` with the dimension names. "Askable"
|
|
1585
|
+
is the conjunction the turn node already computes as `askUserAvailable` (v2,
|
|
1586
|
+
wiring up, budget left, ask-rounds cap unreached, principal reachable,
|
|
1587
|
+
non-final turn) with the checklist's own part (unknown, and the topic unasked
|
|
1588
|
+
in this negotiation). Every one of those conditions failing REOPENS the
|
|
1589
|
+
verdict, which is what keeps the floor from being a deadlock: a spent budget,
|
|
1590
|
+
an unreachable principal, a settled checklist or the last turn all leave the
|
|
1591
|
+
verdict exactly where it was. Fails open on an unauthored checklist;
|
|
1592
|
+
`advocate`/v1 untouched; #1463's decline law still applies independently.
|
|
1593
|
+
|
|
1594
|
+
On a premature verdict the turn node logs/traces `negotiation_conclude_premature`
|
|
1595
|
+
and re-issues the turn ONCE, naming the open dimensions and leaving two moves:
|
|
1596
|
+
score the dimension from something a principal actually STATED, or ask the
|
|
1597
|
+
client whose fact it is. Unlike the anti-echo re-issue — which hard-refuses
|
|
1598
|
+
`ask_user`, since a repeated message says nothing about whether a consultation
|
|
1599
|
+
is warranted — an ask drafted on THIS re-issue is the outcome the floor exists
|
|
1600
|
+
to produce, so it is offered in the seat vocabulary and flows through the
|
|
1601
|
+
ordinary admission and park path. That required the three ask gates
|
|
1602
|
+
(reachability, availability/policy, the five-part rule) to become one function
|
|
1603
|
+
the re-issue faces too; policy admission is re-run for a re-issued ask, because
|
|
1604
|
+
the eligibility computed for the refused draft was a judgment about an action
|
|
1605
|
+
that no longer exists.
|
|
1606
|
+
|
|
1607
|
+
- **When the model still refuses, the graph fires the arrow itself.** If the turn
|
|
1608
|
+
that would persist still leaves no ask on the table while an askable unknown
|
|
1609
|
+
stands, the drafted turn is coerced to `ask_user` carrying the top askable
|
|
1610
|
+
DIMENSION, and parks exactly as an agent-drafted ask does — `input_required`,
|
|
1611
|
+
expiry timer, questioner enqueue. Bounded at one per negotiation per principal
|
|
1612
|
+
via a new graph-only `askUser.guaranteed` mark read back off the persisted
|
|
1613
|
+
turn (the turn node strips any agent-claimed mark, so the floor is the field's
|
|
1614
|
+
only writer), and it consumes budget and an ask round like any other ask
|
|
1615
|
+
because the record it writes is the same one every accounting reads.
|
|
1616
|
+
|
|
1617
|
+
Coercion rather than "persist the turn and park beside it": every accounting
|
|
1618
|
+
the protocol has — the per-principal budget, the asked-topics record, the
|
|
1619
|
+
negotiation-wide ask-rounds cap — is read off persisted `ask_user` turns, so a
|
|
1620
|
+
park riding alongside a `counter` would spend a person's attention while the
|
|
1621
|
+
record showed nothing spent and leave the same dimension askable next turn.
|
|
1622
|
+
And after the re-issue the drafted action is frequently terminal, where
|
|
1623
|
+
persisting it would END the negotiation — there is no "in addition" available.
|
|
1624
|
+
What coercion costs is the drafted message, and only where it should be: a
|
|
1625
|
+
terminal turn's message is dropped with the action it belonged to (#1463's
|
|
1626
|
+
rule, for #1463's reason), while a non-terminal message is kept and persisted
|
|
1627
|
+
— a real contribution to the exchange, after which the seat parks instead of
|
|
1628
|
+
handing the turn over. Traced as `negotiation_ask_guaranteed` with the
|
|
1629
|
+
dimension.
|
|
1630
|
+
|
|
1631
|
+
This is NOT the pre-#1455 inferred consultation. That fired from action enums
|
|
1632
|
+
with no content behind them and produced "would you be open to connecting?";
|
|
1633
|
+
this fires from a named dimension the agent itself wrote and itself scored
|
|
1634
|
+
unknown, and the api's question-message author already reads
|
|
1635
|
+
`askUser.dimension` off the parked turn, so what reaches the client is a
|
|
1636
|
+
question about that dimension. `NegotiationInflightContext.dimension`
|
|
1637
|
+
(additive, optional) carries the same thing on the questioner payload.
|
|
1638
|
+
|
|
1639
|
+
The OPENING turn is deliberately outside all of this. The checklist is authored
|
|
1640
|
+
there and the authoring instruction REQUIRES a dimension the record does not
|
|
1641
|
+
settle, so an open dimension on turn 0 is the shape the protocol asked for, not
|
|
1642
|
+
a dodge — and a floor that bound there would park every negotiation before it
|
|
1643
|
+
ever made contact. Turn 0 already has its own designed consult, the pre-contact
|
|
1644
|
+
verdict, bounded per signal.
|
|
1645
|
+
|
|
1646
|
+
- **The verdict prompt's escape hatch is now conditional.** "What remains unknown
|
|
1647
|
+
is the kind of thing two people settle in a first conversation" waved verdicts
|
|
1648
|
+
through unconditionally; the reference behaviour opens that hatch only once the
|
|
1649
|
+
question budget is spent. `CHECKLIST_VERDICT_RULE` now says so: while budget
|
|
1650
|
+
remains and the client is reachable, an unknown that is theirs to settle is
|
|
1651
|
+
asked before any verdict. The basis discipline also gains one line — the reason
|
|
1652
|
+
a match was suggested is an inference drawn by something that never spoke to
|
|
1653
|
+
either principal, so it can no more score a dimension than a profile can.
|
|
1654
|
+
|
|
1655
|
+
Protocol 23.2.0 → 23.3.0. No flags; ships on.
|
|
1656
|
+
|
|
1657
|
+
## 23.2.0 - 2026-08-20
|
|
1658
|
+
|
|
1659
|
+
### Fixed
|
|
1660
|
+
|
|
1661
|
+
- **No turn may repeat a message already on the record.** A counterparty asked what
|
|
1662
|
+
a phrase in the client's own signal meant; the answering agent could not consult
|
|
1663
|
+
its (unreachable) principal and its record did not settle the phrase, so with no
|
|
1664
|
+
legal move left it copied the question back word for word. Both models then
|
|
1665
|
+
locked — reproducing text already in context is close to deterministic — and the
|
|
1666
|
+
negotiation spent its remaining turns exchanging two byte-identical messages
|
|
1667
|
+
before one side declined citing "repeated lack of clarity … despite five
|
|
1668
|
+
inquiries". The turn node now compares each drafted message against every
|
|
1669
|
+
message already in the negotiation: an exact repeat is never persisted, the turn
|
|
1670
|
+
is re-issued ONCE with the repeated text quoted back and an instruction to
|
|
1671
|
+
contribute or conclude, and a second repeat ends the run as the new
|
|
1672
|
+
`outcome.reason: "repetition"` — never as a decline, because nobody decided
|
|
1673
|
+
anything. Terminal turns are exempt (a turn that ends the negotiation cannot
|
|
1674
|
+
loop, and refusing one would turn a successful accept into a stall);
|
|
1675
|
+
message-less turns have nothing to duplicate. Deadlock detection (IND-428)
|
|
1676
|
+
could not cover this: its four-turn threshold arrives one turn before a
|
|
1677
|
+
six-turn cap, after the loop has already consumed the negotiation.
|
|
1678
|
+
- **The unreachable-principal rule gains the move the corner actually needed.**
|
|
1679
|
+
`PRINCIPAL_UNREACHABLE_RULE` said never stall and never route the client's
|
|
1680
|
+
question to the other side, but named no move for the case that occurred: the
|
|
1681
|
+
COUNTERPARTY asks something client-authoritative that the record does not
|
|
1682
|
+
settle. The rule now says to state the limit of the record — "X's signal says
|
|
1683
|
+
Y; it does not specify further" is a complete answer — and to let the
|
|
1684
|
+
counterparty score that dimension unknown, never repeating or mirroring their
|
|
1685
|
+
question and never inventing an answer the record does not hold.
|
|
1686
|
+
- **A decline needs a conflict.** The verdict law ("an unknown is not a reason to
|
|
1687
|
+
end anything; pass stays reserved for conflict") was prompt-only, and the prompt
|
|
1688
|
+
lost. A drafted `decline`/`reject` over an authored checklist that holds no
|
|
1689
|
+
`conflict` dimension is now refused — logged as `negotiation_decline_inadmissible`
|
|
1690
|
+
with the unknowns that stood in for one — and coerced to the conservative
|
|
1691
|
+
non-terminal fallback, its terminal message dropped with the action it belonged
|
|
1692
|
+
to. On the final turn, where the seat's vocabulary is accept-or-decline, the
|
|
1693
|
+
decline stands but the violation is recorded rather than manufactured silently.
|
|
1694
|
+
Assessing stances only; fails open on an unauthored checklist; `advocate` is
|
|
1695
|
+
untouched.
|
|
1696
|
+
|
|
1697
|
+
### Added
|
|
1698
|
+
|
|
1699
|
+
- `NegotiationOutcome.reason` gains `"repetition"`, and `NegotiationAgentInput`
|
|
1700
|
+
gains `antiEcho` (the repeated text, quoted back on a re-issue).
|
|
1701
|
+
- `assessDeclineAdmissibility` in the checklist contracts: the verdict law as a
|
|
1702
|
+
pure function, beside `assessAskAdmissibility`.
|
|
1703
|
+
- Machine-fault reasons (`agent_error`, `repetition`) are filtered out of the
|
|
1704
|
+
discovery vocabulary by an allow-list rather than a deny-list, so a new
|
|
1705
|
+
negotiation reason can never silently cross that boundary.
|
|
1706
|
+
|
|
1707
|
+
## 23.1.1 - 2026-08-19
|
|
1708
|
+
|
|
1709
|
+
### Fixed
|
|
1710
|
+
|
|
1711
|
+
- **A negotiation that has already spoken is no longer re-screened.** The outreach
|
|
1712
|
+
gate asks whether to make first contact, and `routeAfterInit` ran it on every
|
|
1713
|
+
continuation that was not an exact `ask_user` resume. An error-stalled negotiation
|
|
1714
|
+
recovered through `negotiation-run-existing` — the documented recovery path — was
|
|
1715
|
+
therefore re-screened two hours after its outreach landed; the gate passed, and an
|
|
1716
|
+
infrastructure failure plus its own recovery turned into a terminal `rejected`
|
|
1717
|
+
the counterparty was never given the chance to answer. Eligibility is now
|
|
1718
|
+
pre-contact, scoped to the negotiation (new `negotiationHasMadeContact`): a new
|
|
1719
|
+
opportunity reusing an existing `dm_pair` is still screened (IND-563), a
|
|
1720
|
+
screen-only or all-`ask_user` history is still pre-contact, and a persisted turn
|
|
1721
|
+
addressed to the counterparty ends the question for good.
|
|
1722
|
+
- **A first-turn `withdraw` on a contacted continuation persists as a real
|
|
1723
|
+
retraction.** The IND-564 guard read `outreachOpened`, which is per-task, so a
|
|
1724
|
+
continuation of a negotiation whose outreach was sent in an earlier session was
|
|
1725
|
+
treated as never-contacted and routed to the quiet `screened_out` outcome. The
|
|
1726
|
+
guard now applies only where nothing was ever sent; a withdraw against a message
|
|
1727
|
+
the counterparty received is recorded as the move it is.
|
|
1728
|
+
- **`screened_out` can no longer be stamped on a negotiation whose messages
|
|
1729
|
+
contradict it.** `finalizeNode` gates both routes to the label — the screen-node
|
|
1730
|
+
block and the opening-turn refusal — on the same pre-contact predicate, so the one
|
|
1731
|
+
outcome that claims nothing was ever sent is unfalsifiable at the point of record.
|
|
1732
|
+
|
|
1733
|
+
## 23.1.0 - 2026-08-19
|
|
1734
|
+
|
|
1735
|
+
### Fixed
|
|
1736
|
+
|
|
1737
|
+
- **Retrieval scores no longer clamp at a flat ceiling.** The multi-signal bonus in
|
|
1738
|
+
`mergeStrategyCandidates` was added to the raw similarity and then clamped
|
|
1739
|
+
(`Math.min(raw + boost, 1)`), so candidates found by enough strategies all landed
|
|
1740
|
+
on exactly 1.0. Candidates enter evaluation strictly by rank, so a head cluster of
|
|
1741
|
+
identical maxima crowded genuine matches out of the only evaluated batch. The bonus
|
|
1742
|
+
now consumes the headroom above the raw score (new internal
|
|
1743
|
+
`opportunities/opportunity.similarity.ts`): strictly monotone in the raw score,
|
|
1744
|
+
and 1.0 is reachable only by a vector that actually scored 1.0.
|
|
1745
|
+
- **Evaluation continues past a batch that passes nothing.** `remainingCandidates`
|
|
1746
|
+
was written and never read — there was no second batch, so a run whose top-ranked
|
|
1747
|
+
candidates all failed reported `evaluator_rejected_all` while the real matches sat
|
|
1748
|
+
unevaluated behind them. The evaluation node now walks up to
|
|
1749
|
+
`MAX_EVAL_BATCHES_PER_RUN` (3) batches of 25 while no candidate passes, and stops
|
|
1750
|
+
as soon as one does.
|
|
1751
|
+
- **A stranded tail is reported as a bound, not as a rejection.** When the batch bound
|
|
1752
|
+
is reached with candidates left, the trace carries an `evaluation_bound` node with
|
|
1753
|
+
the never-evaluated count.
|
|
1754
|
+
|
|
1755
|
+
### Changed
|
|
1756
|
+
|
|
1757
|
+
- **`invokeEntityBundle` under `returnAll: true` now returns dropped verdicts too**,
|
|
1758
|
+
tagged with `rejection: { candidateId, reason }` (`not_accepted` |
|
|
1759
|
+
`incomplete_actors` | `unsupported_claim`) and carrying no actors. Previously a
|
|
1760
|
+
candidate the model explicitly rejected, and one whose accepted verdict a guard
|
|
1761
|
+
dropped, were both indistinguishable from silence, and the discovery trace labelled
|
|
1762
|
+
every one of them "No evaluation returned for this candidate". Callers that
|
|
1763
|
+
persist must filter on `rejection === undefined`; `returnAll: false` is unchanged.
|
|
1764
|
+
|
|
1765
|
+
## 23.0.0 - 2026-08-19
|
|
1766
|
+
|
|
1767
|
+
### Added
|
|
1768
|
+
|
|
1769
|
+
- **The checklist negotiation core** (docs/plans/2026-08-19-checklist-negotiations.md
|
|
1770
|
+
§2–§4, §6). A negotiation under the assessing stances now runs on an explicit,
|
|
1771
|
+
pre-registered checklist: 3–5 dimensions authored on turn 1 from the two
|
|
1772
|
+
intents alone (`mutual_want` always present), frozen after, re-scored each
|
|
1773
|
+
turn from the commitment record, with the verdict a function of the scores.
|
|
1774
|
+
New domain module `negotiations/negotiation.checklist.contracts.ts` (exported
|
|
1775
|
+
from the package root): `NegotiationChecklistSchema`, `authorChecklist`,
|
|
1776
|
+
`reconcileChecklist`, `checklistFromTurns`, `checklistVerdictState`,
|
|
1777
|
+
`assessAskAdmissibility`, `renderChecklistSection`,
|
|
1778
|
+
`QUESTION_BUDGET_PER_PRINCIPAL`, `configuredQuestionBudgetPerPrincipal`,
|
|
1779
|
+
plus the DTOs in `shared/schemas/negotiation-checklist.schema.ts`.
|
|
1780
|
+
- **`ask_user` payload**: optional `dimension` and `answerhood`
|
|
1781
|
+
(`{ ok_when, conflict_when }`). An ask names exactly one open dimension and
|
|
1782
|
+
declares in advance what answers score it — the pivotality proof. Both are
|
|
1783
|
+
optional, so v1 turns, external agents and the enum-only path validate
|
|
1784
|
+
unchanged.
|
|
1785
|
+
- **Turn payload**: optional `checklist`, carried on every turn under the
|
|
1786
|
+
protocol. The turn record is the checklist's only store — no new tables, and
|
|
1787
|
+
a continuation recovers the frozen dimensions from the messages it already
|
|
1788
|
+
reads.
|
|
1789
|
+
- **Question block**: optional `dimension` on a block question, the checklist
|
|
1790
|
+
dimension a park is about, for the step's label. Presentation only; routing
|
|
1791
|
+
is still the negotiation ref alone. Blocks without it parse unchanged, so the
|
|
1792
|
+
fail-closed parser stays backward-compatible.
|
|
1793
|
+
- **Per-principal question budget**: at most `QUESTION_BUDGET_PER_PRINCIPAL`
|
|
1794
|
+
(3) questions per principal per negotiation, the turn-0 pre-contact consult
|
|
1795
|
+
included and post-stall parks counted. `countPrincipalAskUserTurns` exposes
|
|
1796
|
+
the count off the message record.
|
|
1797
|
+
|
|
1798
|
+
### Changed
|
|
1799
|
+
|
|
1800
|
+
- **BREAKING** — `ConsultationEligibilityInput.previouslyConsulted` is now
|
|
1801
|
+
`consultationBudgetSpent`: the one-consultation ration became a budget, and
|
|
1802
|
+
a ration of one is that budget with `total = 1`. Callers pass "this
|
|
1803
|
+
principal's budget for this negotiation is spent" instead of "they have
|
|
1804
|
+
consulted before".
|
|
1805
|
+
- **Negotiator stance contracts restructured** around the checklist protocol.
|
|
1806
|
+
The evidence-provenance rule (#1448) is now the `basis` discipline — an
|
|
1807
|
+
agent's own conclusions are decisions, not commitments, so they cannot score
|
|
1808
|
+
a dimension — and the responder verification rules (#1446) are now the
|
|
1809
|
+
responding seat's scoring duty. Neither duty was dropped; both became rules
|
|
1810
|
+
about what may score a dimension, and the repair path enforces them (an `ok`
|
|
1811
|
+
with no basis is repaired to `unknown`). New predicate `stanceUsesChecklist`.
|
|
1812
|
+
`advocate` is untouched, prompt and generation schema alike — the golden
|
|
1813
|
+
prompt matrix still passes byte-for-byte.
|
|
1814
|
+
- `negotiationAskRoundsCap()` takes `{ checklist }` and defaults to
|
|
1815
|
+
`CHECKLIST_NEGOTIATION_ASK_ROUNDS_CAP` (both principals' budgets plus one
|
|
1816
|
+
post-stall park) under the checklist protocol; the pre-checklist default
|
|
1817
|
+
stays 3. An explicit `NEGOTIATION_ASK_ROUNDS_CAP` still wins.
|
|
1818
|
+
- `AskUserOpts` is now `TurnVocabularyOpts` (`{ askUser, checklist }`); the old
|
|
1819
|
+
name remains as a deprecated alias.
|
|
1820
|
+
|
|
23
1821
|
## 22.0.0 - 2026-08-18
|
|
24
1822
|
|
|
25
1823
|
### Removed
|
|
@@ -761,6 +2559,49 @@ No public API change: all 441 exported symbols are byte-identical to 13.2.0, and
|
|
|
761
2559
|
|
|
762
2560
|
## [Unreleased]
|
|
763
2561
|
|
|
2562
|
+
### Removed
|
|
2563
|
+
|
|
2564
|
+
- **Breaking (38.0.0): single-path opportunities.** Discovery no longer creates
|
|
2565
|
+
opportunities. It records one `discovery_match_candidates` row per pair, keyed by
|
|
2566
|
+
`pairKeyOf(networkId, intentA, intentB)`, and the `opportunities` row is INSERTed at
|
|
2567
|
+
kickoff by `createAndOpen` when a principal's PersonalAgent decides to reach out.
|
|
2568
|
+
- `PersonalAgentMatch.opportunityId` is replaced by
|
|
2569
|
+
`ref: { kind: 'candidate' | 'opportunity'; id: string }`. Read it with
|
|
2570
|
+
`matchRefId(match)`; build one with `opportunityRef(id)`.
|
|
2571
|
+
- `PersonalAgentOpportunityPort` requires `createAndOpen`.
|
|
2572
|
+
- `OpportunityStatus` loses `latent` and `draft`. An opportunity is born
|
|
2573
|
+
`negotiating`; there is no pre-kickoff state.
|
|
2574
|
+
- The `introducer` actor role is removed, with its `approved` field,
|
|
2575
|
+
`updateOpportunityActorApproval`, and every visibility rule that keyed on it.
|
|
2576
|
+
`canUserSeeOpportunity` now answers one question — is the viewer an actor.
|
|
2577
|
+
- Removed exports: `MaintenanceGraphFactory`, `MaintenanceGraphDatabase`,
|
|
2578
|
+
`MaintenanceGraphCache`, `MaintenanceGraphQueue`, `createIntroduction`,
|
|
2579
|
+
`approveIntroduction`, `sendOpportunity`, `evaluateIntroduction`,
|
|
2580
|
+
`validateIntroduction`, `IntroductionRequest`, `persistOpportunities`,
|
|
2581
|
+
`StampNewbornOpportunitiesFn`, `StampNewbornOpportunitiesInput`,
|
|
2582
|
+
`OpportunityPersistenceOutcome`, and the `radar.health` scoring module.
|
|
2583
|
+
- `operationMode` narrows to `create | read | update | delete`.
|
|
2584
|
+
- Discovery sources narrow to `query`; `premise-similarity`,
|
|
2585
|
+
`context-similarity` and `context-to-intent` are gone, as are their evidence
|
|
2586
|
+
kinds.
|
|
2587
|
+
- Hosts must implement `upsertDiscoveryMatchCandidates` and
|
|
2588
|
+
`listPendingCandidatesForIntent`.
|
|
2589
|
+
- **Breaking (38.0.0): `QuestionRecoverySnapshot` drops its discovery-completion
|
|
2590
|
+
fields.** `completionSource` narrows to `z.enum(["intent_creation"])` — the
|
|
2591
|
+
`from_intent`/`discovery_run` values belonged to the post-discovery
|
|
2592
|
+
recovery-question generator, retired in `6a3b65b0e` with no writer left.
|
|
2593
|
+
`rejectedNegotiationCount` and `runId` are removed for the same reason.
|
|
2594
|
+
Existing persisted `questions.detection` rows written before the retirement
|
|
2595
|
+
may still carry the old values; nothing in the host parses them against this
|
|
2596
|
+
schema at read time.
|
|
2597
|
+
|
|
2598
|
+
### Added
|
|
2599
|
+
|
|
2600
|
+
- `pairKeyOf`, `DiscoveryMatchCandidate`, `CreateDiscoveryMatchCandidateData`,
|
|
2601
|
+
`DiscoveryMatchCandidateStatus`, `CreateAndOpenResult`, `PersonalAgentMatchRef`,
|
|
2602
|
+
`matchRefId`, `opportunityRef`, `OpportunityEvidence`.
|
|
2603
|
+
|
|
2604
|
+
|
|
764
2605
|
### Changed
|
|
765
2606
|
- Behaviour-neutral internal refactor (16.1.1): split the six largest modules and hoist every graph node to a top-level function. The opportunity graph is now the discovery pipeline only — its eight non-pipeline modes (read, update, delete, send, negotiate_existing, approve_introduction, and the two introduction stages) are plain functions on `OpportunityGraphFactory` instead of `operationMode` conditional-edge routing. `database.interface.ts` becomes a barrel over entity, query-group, and capability-view modules; every `Pick<Database, ...>` resolves as before. The opportunity presentation cluster is one module. `opportunity.graph.ts` 4167 → 250 lines, `database.interface.ts` 2925 → 17, `negotiation.graph.ts` 1619 → 111, `opportunity.tools.ts` 1200 → 354, `enrichment.tools.ts` 1198 → 178, `intent.graph.ts` 1091 → 174. No public export, feature flag, or environment variable changed.
|
|
766
2607
|
- Move the opportunity-presentation review checklist into `src/opportunity/AGENTS.md` and repoint the `opportunity.safe-presentation.ts` and `discriminator.adjustments.ts` comments at it. Comment-only; no runtime change.
|