---
id: ATS-CRM-DQ-016
scope: CAP-CRM-DQ-016
product_area: crm
module: data-quality
revision: 1
status: proposed
source_sha:
  services-crm: a8d1364f1dd44b723bb5f9acba12f983e9ec8d69
  react-console: baf6dae382d6f41dce976c7f848667ccc37e076f
scenarios:
  - id: ATS-CRM-DQ-016-01
    title: An unready preview cannot execute
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-01
    preconditions: A plan has an unanswered required question.
    steps: Submit execution.
    expected: The service refuses readiness and names the question.
    negative: true
    data_needs: The existing scenario setup supplies the required records.
    bound_to:
      - TST-CRM-DQ-183
    provenance: test
    source: >-
      services-crm:modules/merges/tests/e2e/merges.e2e.spec.js#refuses the
      execution request as a plan that is not ready
    category: validation
    execution_sources:
      - >-
        services-crm:modules/merges/tests/e2e/merges.e2e.spec.js#refuses the
        execution request as a plan that is not ready
      - >-
        services-crm:modules/merges/tests/e2e/merges.e2e.spec.js#names the
        conflict that is still open, so a console can take the reader to it
  - id: ATS-CRM-DQ-016-02
    title: Execution rejects an approval with new dependent work
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-02
    preconditions: A task arrives on an absorbed record after approval.
    steps: >-
      Execute with and without a supplied fingerprint, reopen the preview and
      execute again.
    expected: >-
      Both old approvals fail with the task change; renewed review permits
      execution.
    negative: true
    data_needs: The existing scenario setup supplies the required records.
    bound_to:
      - TST-CRM-DQ-181
      - TST-CRM-DQ-183
    provenance: test
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/approval-binding.integration.spec.js#refuses
      the execution carrying the approved hash as plan_stale
    category: validation
    execution_sources:
      - >-
        services-crm:modules/merges/tests/integration/services/merges/approval-binding.integration.spec.js#refuses
        the execution carrying the approved hash as plan_stale
      - >-
        services-crm:modules/merges/tests/integration/services/merges/approval-binding.integration.spec.js#refuses
        an execution that submits no hash too, because the stored plan is the
        one last shown
      - >-
        services-crm:modules/merges/tests/integration/services/merges/approval-binding.integration.spec.js#executes
        once the plan is looked at again and confirmed, moving the task the
        reviewer saw
      - >-
        services-crm:modules/merges/tests/e2e/merges.e2e.spec.js#queues no merge
        for a plan it refused
  - id: ATS-CRM-DQ-016-03
    title: Presentation changes leave approval material stable
    level: unit
    proves:
      - BR-CAP-CRM-DQ-016-03
    preconditions: 'Prepare previews differing only in wording, estimates or suggestions.'
    steps: Compute their material fingerprints.
    expected: The fingerprints remain equal.
    negative: false
    data_needs: The existing scenario setup supplies the required records.
    bound_to:
      - TST-CRM-DQ-181
    provenance: test
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/lookup-labels.integration.spec.js#answers
      the same material hash, a name being no part of what staff are approving
    category: invariant
    execution_sources:
      - >-
        services-crm:modules/merges/tests/integration/services/merges/lookup-labels.integration.spec.js#answers
        the same material hash, a name being no part of what staff are approving
      - >-
        services-crm:modules/merges/tests/unit/services/planning/survivor-recommendation.spec.js#is
        no part of the material plan hash, changing no value of any record
      - >-
        services-crm:modules/merges/tests/unit/services/planning/long-running-merge.spec.js#is
        no part of the material plan hash, so a slower estimate can never make
        an approved plan stale
  - id: ATS-CRM-DQ-016-04
    title: Repeated confirmation returns the same durable work
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-04
    preconditions: A plan is ready.
    steps: Submit sequential and simultaneous executions.
    expected: One merge and job exist and repeat submissions report no creation.
    negative: false
    data_needs: The existing scenario setup supplies the required records.
    bound_to:
      - TST-CRM-DQ-181
      - TST-CRM-DQ-183
    provenance: test
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/merge-settlement.integration.spec.js#answers
      both requests the same merge
    category: concurrency
    execution_sources:
      - >-
        services-crm:modules/merges/tests/integration/services/merges/merge-settlement.integration.spec.js#answers
        both requests the same merge
      - >-
        services-crm:modules/merges/tests/integration/services/merges/merge-execution.integration.spec.js#answers
        a repeated execute request with the merge that already exists
      - >-
        services-crm:modules/merges/tests/integration/services/merges/merge-execution.integration.spec.js#tells
        a repeated execute request it created nothing
      - >-
        services-crm:modules/merges/tests/e2e/merges.e2e.spec.js#answers the
        same merge to a second execution request, rather than merging twice
  - id: ATS-CRM-DQ-016-05
    title: Reconciliation settles jobs that never started
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-05
    preconditions: A queued merge has lost its job start.
    steps: Run reconciliation.
    expected: The job and merge record failure with an explanation and the plan reopens.
    negative: false
    data_needs: The existing scenario setup supplies the required records.
    bound_to:
      - TST-CRM-DQ-183
      - TST-CRM-DQ-181
    provenance: test
    source: >-
      services-crm:modules/merges/tests/integration/services/jobs/job-reconciliation.integration.spec.js#settles
      the job failed, rather than leaving it in flight for ever
    category: failure
    execution_sources:
      - >-
        services-crm:modules/merges/tests/e2e/merges.e2e.spec.js#answers the
        execution request with the merge it queued and the job that will run it
      - >-
        services-crm:modules/merges/tests/integration/services/jobs/job-reconciliation.integration.spec.js#settles
        the job failed, rather than leaving it in flight for ever
      - >-
        services-crm:modules/merges/tests/integration/services/jobs/job-reconciliation.integration.spec.js#gives
        the merge the code Internal and says the job did not finish
  - id: ATS-CRM-DQ-016-06
    title: Transaction failures leave no partial merge
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-06
    preconditions: Prepare stale-under-lock and participant-refusal cases.
    steps: Execute both.
    expected: Each failure is recorded without moved records or new aliases.
    negative: true
    data_needs: The existing scenario setup supplies the required records.
    bound_to:
      - TST-CRM-DQ-181
    provenance: test
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/approval-binding.integration.spec.js#fails
      the merge Stale inside its transaction rather than moving a task nobody
      approved
    category: failure
    execution_sources:
      - >-
        services-crm:modules/merges/tests/integration/services/merges/approval-binding.integration.spec.js#fails
        the merge Stale inside its transaction rather than moving a task nobody
        approved
      - >-
        services-crm:modules/merges/tests/integration/services/merges/merge-execution.integration.spec.js#fails
        the merge with the code Stale
      - >-
        services-crm:modules/merges/tests/integration/services/merges/toy-participant.integration.spec.js#writes
        no alias for a merge that did not happen
  - id: ATS-CRM-DQ-016-07
    title: Overlapping merges have one winner
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-07
    preconditions: Two ready plans share a contact.
    steps: Run both concurrently.
    expected: >-
      One succeeds, the other names already-merged participants and its other
      survivor remains untouched.
    negative: true
    data_needs: The existing scenario setup supplies the required records.
    bound_to:
      - TST-CRM-DQ-181
    provenance: test
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/overlapping-merges.integration.spec.js#lets
      exactly one of the two merges happen
    category: concurrency
    execution_sources:
      - >-
        services-crm:modules/merges/tests/integration/services/merges/overlapping-merges.integration.spec.js#lets
        exactly one of the two merges happen
      - >-
        services-crm:modules/merges/tests/integration/services/merges/overlapping-merges.integration.spec.js#gives
        the merge that did not happen the code AlreadyMerged
      - >-
        services-crm:modules/merges/tests/integration/services/merges/overlapping-merges.integration.spec.js#leaves
        the other survivor byte for byte as it was, because its merge rolled
        back
  - id: ATS-CRM-DQ-016-08
    title: Locks prevent destructive combination
    level: unit
    proves:
      - BR-CAP-CRM-DQ-016-08
    preconditions: Prepare a locked participant and a locked detail variant.
    steps: Build their plans.
    expected: Both variants are blocked.
    negative: true
    data_needs: The existing scenario setup supplies the required records.
    bound_to:
      - >-
        services-crm:modules/merges/tests/unit/services/planning/merge-decisions.spec.js#blocks
        the merge when a participant is locked
      - >-
        services-crm:modules/merges/tests/unit/services/planning/merge-decisions.spec.js#blocks
        the merge when an element of a participant is locked
    provenance: test
    source: >-
      services-crm:modules/merges/tests/unit/services/planning/merge-decisions.spec.js#blocks
      the merge when a participant is locked
    category: validation
    execution_sources:
      - >-
        services-crm:modules/merges/tests/unit/services/planning/merge-decisions.spec.js#blocks
        the merge when a participant is locked
      - >-
        services-crm:modules/merges/tests/unit/services/planning/merge-decisions.spec.js#blocks
        the merge when an element of a participant is locked
    binding_note: >-
      The exact unit-test references remain bound as engineering evidence; unit
      files are not executable suite artifacts.
  - id: ATS-CRM-DQ-016-09
    title: Size limits distinguish refusal and a long-running warning
    level: unit
    proves:
      - BR-CAP-CRM-DQ-016-09
    preconditions: 'Prepare 100,001-row and 10,001-row plans.'
    steps: Compute both.
    expected: >-
      The larger is blocked and the smaller is large with its duration and
      editing warning.
    negative: false
    data_needs: The existing scenario setup supplies the required records.
    bound_to:
      - >-
        services-crm:modules/merges/tests/unit/services/planning/merge-decisions.spec.js#blocks
        a merge above the row ceiling of this release (decision D7)
      - >-
        services-crm:modules/merges/tests/unit/services/planning/merge-decisions.spec.js#calls
        an execution above ten thousand rows large, without blocking it
      - >-
        services-crm:modules/merges/tests/unit/services/planning/long-running-merge.spec.js#is
        raised for that plan, the execution class being the whole of the
        threshold
    provenance: test
    source: >-
      services-crm:modules/merges/tests/unit/services/planning/merge-decisions.spec.js#blocks
      a merge above the row ceiling of this release (decision D7)
    category: boundary
    execution_sources:
      - >-
        services-crm:modules/merges/tests/unit/services/planning/merge-decisions.spec.js#blocks
        a merge above the row ceiling of this release (decision D7)
      - >-
        services-crm:modules/merges/tests/unit/services/planning/merge-decisions.spec.js#calls
        an execution above ten thousand rows large, without blocking it
      - >-
        services-crm:modules/merges/tests/unit/services/planning/long-running-merge.spec.js#is
        raised for that plan, the execution class being the whole of the
        threshold
    binding_note: >-
      The exact unit-test references remain bound as engineering evidence; unit
      files are not executable suite artifacts.
  - id: ATS-CRM-DQ-016-10
    title: A failed attempt remains visible before a new attempt
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-10
    preconditions: A participant refuses execution.
    steps: Read the restored plan and execute again.
    expected: The decisions remain and a different merge records the new attempt.
    negative: false
    data_needs: The existing scenario setup supplies the required records.
    bound_to:
      - TST-CRM-DQ-181
    provenance: test
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/merge-settlement.integration.spec.js#returns
      the plan to the status it had before it was executed, rather than leaving
      it executing
    category: transition
    execution_sources:
      - >-
        services-crm:modules/merges/tests/integration/services/merges/merge-settlement.integration.spec.js#returns
        the plan to the status it had before it was executed, rather than
        leaving it executing
      - >-
        services-crm:modules/merges/tests/integration/services/merges/merge-settlement.integration.spec.js#answers
        the reopened plan to a reader, re-planned against the records and ready
        again
      - >-
        services-crm:modules/merges/tests/integration/db/record-merges.table.integration.spec.js#takes
        a new merge of a plan whose every earlier merge failed, which is how a
        failed merge is retried
  - id: ATS-CRM-DQ-016-11
    title: Successful merging adds record audit pointers
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-12
    preconditions: A merge has succeeded.
    steps: Read each participant's audit entry.
    expected: 'The pointers identify the requester, source record, survivor and time.'
    negative: false
    data_needs: The existing scenario setup supplies the required records.
    bound_to:
      - TST-CRM-DQ-181
    provenance: test
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/merged-from-history.integration.spec.js#says
      who merged which record into which, and when: the merge pointer
    category: rule
    execution_sources:
      - >-
        services-crm:modules/merges/tests/integration/services/merges/merged-from-history.integration.spec.js#says
        who merged which record into which, and when: the merge pointer
  - id: ATS-CRM-DQ-016-12
    title: Contact subscribers receive the committed outcome
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-13
    preconditions: Register a contact-merge subscriber.
    steps: Execute the two-contact combination.
    expected: >-
      One workspace-scoped message identifies the survivor and absorbed
      identities without system fields.
    negative: false
    data_needs: The existing scenario setup supplies the required records.
    bound_to:
      - TST-CRM-DQ-183
    provenance: test
    source: >-
      services-crm:modules/merges/tests/e2e/business-events.e2e.spec.js#sends
      one message for the merge, to the one subscriber, and deletes its queue
      row
    category: interaction
    execution_sources:
      - >-
        services-crm:modules/merges/tests/e2e/business-events.e2e.spec.js#sends
        one message for the merge, to the one subscriber, and deletes its queue
        row
      - >-
        services-crm:modules/merges/tests/e2e/business-events.e2e.spec.js#hands
        the subscriber the envelope of crm.contact.merged, about the survivor,
        in the merge’s tenant
  - id: ATS-CRM-DQ-016-13
    title: Concurrent edits and duplicate submissions have explicit outcomes
    level: browser
    proves:
      - BR-CAP-CRM-DQ-016-02
      - BR-CAP-CRM-DQ-016-04
      - BR-CAP-CRM-DQ-016-06
      - BR-CAP-CRM-DQ-016-07
    preconditions: >-
      An editor holds an absorbed record and two administrators prepare
      overlapping merges.
    steps: >-
      Edit around approval and execution, run competing merges and repeat
      confirmation.
    expected: >-
      Post-approval edits invalidate the preview, execution locks cause waits,
      one overlapping merge wins and repetition creates no duplicate.
    negative: false
    data_needs: The existing scenario setup supplies the required records.
    bound_to: []
    provenance: proposed
    source: FND-CRM-DQ-031
    category: concurrency
    execution_sources: []
  - id: ATS-CRM-DQ-016-14
    title: Duration estimates apply the measured row rate
    level: unit
    proves:
      - BR-CAP-CRM-DQ-016-15
    preconditions: 'Use touched-row totals of zero, 10,000 and 50,000.'
    steps: Calculate the expected seconds for each total.
    expected: 'The estimates are one, eighteen and eighty-six seconds respectively.'
    negative: false
    data_needs: Use the records and caller described in this scenario.
    bound_to:
      - >-
        services-crm:modules/merges/tests/unit/services/planning/long-running-merge.spec.js#is
        one second for a merge that writes no rows at all, a merge that takes a
        moment still taking one
      - >-
        services-crm:modules/merges/tests/unit/services/planning/long-running-merge.spec.js#is
        eighteen seconds for the ten thousand rows a large execution begins
        above
      - >-
        services-crm:modules/merges/tests/unit/services/planning/long-running-merge.spec.js#is
        the minute and a half phase 4 measured for fifty thousand captured row
        changes
    provenance: test
    source: >-
      services-crm:modules/merges/services/planning/merge-engine.ts:expectedMergeSeconds
    category: rule
    execution_sources:
      - >-
        services-crm:modules/merges/tests/unit/services/planning/long-running-merge.spec.js#is
        one second for a merge that writes no rows at all, a merge that takes a
        moment still taking one
      - >-
        services-crm:modules/merges/tests/unit/services/planning/long-running-merge.spec.js#is
        eighteen seconds for the ten thousand rows a large execution begins
        above
      - >-
        services-crm:modules/merges/tests/unit/services/planning/long-running-merge.spec.js#is
        the minute and a half phase 4 measured for fifty thousand captured row
        changes
    binding_note: >-
      The exact unit-test references remain bound as engineering evidence; unit
      files are not executable suite artifacts.
  - id: ATS-CRM-DQ-016-15
    title: >-
      Observe ready becoming executing after an execution request passes
      submission checks
    category: transition
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-01
      - BR-CAP-CRM-DQ-016-05
    transition:
      model: STATE-CRM-DQ-004
      index: 7
      from: ready
      to: executing
      guard: >-
        Defaults are accepted, readiness and size checks pass, hashes match and
        participants remain available.
      side_effects:
        - atomically create the queued attempt and job
        - start workflow execution after commit
    preconditions: >-
      Arrange ready standing with the transition guard satisfied: Defaults are
      accepted, readiness and size checks pass, hashes match and participants
      remain available.
    steps: An execution request passes submission checks.
    expected: >-
      Read the executing standing and inspect the associated changes: atomically
      create the queued attempt and job; start workflow execution after commit.
    negative: false
    data_needs: >-
      Fixtures for ready, the guard and the affected records; a fixed clock for
      time-dependent changes.
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/approval-binding.integration.spec.js#refuses
      an execution that submits no hash too, because the stored plan is the one
      last shown
    design_sources:
      - STATE-CRM-DQ-004
    note: >-
      The design supplies this transition obligation. A runtime binding requires
      assertions for its guard, destination and associated writes in one
      sequence.
    bound_to: []
    provenance: proposed
    execution_sources: []
  - id: ATS-CRM-DQ-016-16
    title: >-
      Observe executing becoming executed after successful execution commits the
      business transaction
    category: transition
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-06
      - INV-DOM-CRM-DQ-004-04
    transition:
      model: STATE-CRM-DQ-004
      index: 8
      from: executing
      to: executed
      guard: The attempt holds its required participants under lock.
      side_effects:
        - mark the plan executed within that transaction
    preconditions: >-
      Arrange executing standing with the transition guard satisfied: The
      attempt holds its required participants under lock.
    steps: Successful execution commits the business transaction.
    expected: >-
      Read the executed standing and inspect the associated changes: mark the
      plan executed within that transaction.
    negative: false
    data_needs: >-
      Fixtures for executing, the guard and the affected records; a fixed clock
      for time-dependent changes.
    source: >-
      services-crm:modules/merges/services/merges/merge-execution.ts:executeMerge
    design_sources:
      - STATE-CRM-DQ-004
    note: >-
      The design supplies this transition obligation. A runtime binding requires
      assertions for its guard, destination and associated writes in one
      sequence.
    bound_to: []
    provenance: proposed
    execution_sources: []
  - id: ATS-CRM-DQ-016-17
    title: >-
      Observe executing becoming ready after executor or reconciliation settles
      a failed ready attempt
    category: transition
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-10
    transition:
      model: STATE-CRM-DQ-004
      index: 9
      from: executing
      to: ready
      guard: The plan remains executing and its prior preview was ready.
      side_effects:
        - fail the attempt and reopen the plan atomically
        - retain decisions for the next recomputation
    preconditions: >-
      Arrange executing standing with the transition guard satisfied: The plan
      remains executing and its prior preview was ready.
    steps: Executor or reconciliation settles a failed ready attempt.
    expected: >-
      Read the ready standing and inspect the associated changes: fail the
      attempt and reopen the plan atomically; retain decisions for the next
      recomputation.
    negative: false
    data_needs: >-
      Fixtures for executing, the guard and the affected records; a fixed clock
      for time-dependent changes.
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/merge-settlement.integration.spec.js#returns
      the plan to the status it had before it was executed, rather than leaving
      it executing
    design_sources:
      - STATE-CRM-DQ-004
    note: >-
      The design supplies this transition obligation. A runtime binding requires
      assertions for its guard, destination and associated writes in one
      sequence.
    bound_to: []
    provenance: proposed
    execution_sources: []
  - id: ATS-CRM-DQ-016-18
    title: >-
      Observe executing becoming needs_decisions after failure settlement finds
      a different prior preview state
    category: transition
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-10
    transition:
      model: STATE-CRM-DQ-004
      index: 10
      from: executing
      to: needs_decisions
      guard: The plan still has executing standing.
      side_effects:
        - restore the stored working state or the fallback needing decisions
    preconditions: >-
      Arrange executing standing with the transition guard satisfied: The plan
      still has executing standing.
    steps: Failure settlement finds a different prior preview state.
    expected: >-
      Read the needs_decisions standing and inspect the associated changes:
      restore the stored working state or the fallback needing decisions.
    negative: false
    data_needs: >-
      Fixtures for executing, the guard and the affected records; a fixed clock
      for time-dependent changes.
    source: >-
      services-crm:modules/merges/services/merges/merge-settlement.ts:statusBeforeExecution
    design_sources:
      - STATE-CRM-DQ-004
    note: >-
      The design supplies this transition obligation. A runtime binding requires
      assertions for its guard, destination and associated writes in one
      sequence.
    bound_to: []
    provenance: proposed
    execution_sources: []
  - id: ATS-CRM-DQ-016-19
    title: >-
      Observe queued becoming running after the task begins the transaction and
      claims the queued attempt
    category: transition
    level: api
    proves:
      - INV-DOM-CRM-DQ-004-01
      - BR-CAP-CRM-DQ-016-05
    transition:
      model: STATE-CRM-DQ-005
      index: 1
      from: queued
      to: running
      guard: The conditional claim must still find queued standing.
      side_effects:
        - apply five-second lock and five-minute statement limits
        - acquire advisory and participant row locks in fixed order
    preconditions: >-
      Arrange queued standing with the transition guard satisfied: The
      conditional claim must still find queued standing.
    steps: The task begins the transaction and claims the queued attempt.
    expected: >-
      Read the running standing and inspect the associated changes: apply
      five-second lock and five-minute statement limits; acquire advisory and
      participant row locks in fixed order.
    negative: false
    data_needs: >-
      Fixtures for queued, the guard and the affected records; a fixed clock for
      time-dependent changes.
    source: >-
      services-crm:modules/merges/services/merges/merge-execution.ts:executeMerge
    design_sources:
      - STATE-CRM-DQ-005
    note: >-
      The design supplies this transition obligation. A runtime binding requires
      assertions for its guard, destination and associated writes in one
      sequence.
    bound_to: []
    provenance: proposed
    execution_sources: []
  - id: ATS-CRM-DQ-016-20
    title: >-
      Observe running becoming succeeded after the complete business transaction
      succeeds
    category: transition
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-06
    transition:
      model: STATE-CRM-DQ-005
      index: 2
      from: running
      to: succeeded
      guard: >-
        Replanning matches approval, participants exist, blockers clear,
        applications accept and the survivor validates.
      side_effects:
        - settle the plan as executed
        - report completed job steps after commit
        - nudge committed contact event delivery
    preconditions: >-
      Arrange running standing with the transition guard satisfied: Replanning
      matches approval, participants exist, blockers clear, applications accept
      and the survivor validates.
    steps: The complete business transaction succeeds.
    expected: >-
      Read the succeeded standing and inspect the associated changes: settle the
      plan as executed; report completed job steps after commit; nudge committed
      contact event delivery.
    negative: false
    data_needs: >-
      Fixtures for running, the guard and the affected records; a fixed clock
      for time-dependent changes.
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/approval-binding.integration.spec.js#fails
      the merge Stale inside its transaction rather than moving a task nobody
      approved
    design_sources:
      - STATE-CRM-DQ-005
    note: >-
      The design supplies this transition obligation. A runtime binding requires
      assertions for its guard, destination and associated writes in one
      sequence.
    bound_to: []
    provenance: proposed
    execution_sources: []
  - id: ATS-CRM-DQ-016-21
    title: >-
      Observe running becoming failed after execution catches a refusal or
      exception
    category: transition
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-06
    transition:
      model: STATE-CRM-DQ-005
      index: 3
      from: running
      to: failed
      guard: Conditional failure settlement still finds queued or running standing.
      side_effects:
        - store failure code and reason
        - reopen an eligible plan
        - report the mapped failed step and leave later steps queued
    preconditions: >-
      Arrange running standing with the transition guard satisfied: Conditional
      failure settlement still finds queued or running standing.
    steps: Execution catches a refusal or exception.
    expected: >-
      Read the failed standing and inspect the associated changes: store failure
      code and reason; reopen an eligible plan; report the mapped failed step
      and leave later steps queued.
    negative: true
    data_needs: >-
      Fixtures for running, the guard and the affected records; a fixed clock
      for time-dependent changes.
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/merge-settlement.integration.spec.js#returns
      the plan to the status it had before it was executed, rather than leaving
      it executing
    design_sources:
      - STATE-CRM-DQ-005
    note: >-
      The design supplies this transition obligation. A runtime binding requires
      assertions for its guard, destination and associated writes in one
      sequence.
    bound_to: []
    provenance: proposed
    execution_sources: []
  - id: ATS-CRM-DQ-016-22
    title: >-
      Observe queued becoming failed after reconciliation closes an attempt
      whose job never completed
    category: transition
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-05
    transition:
      model: STATE-CRM-DQ-005
      index: 4
      from: queued
      to: failed
      guard: Settlement accepts only a still-unfinished attempt.
      side_effects:
        - record internal failure
        - reopen its eligible plan
    preconditions: >-
      Arrange queued standing with the transition guard satisfied: Settlement
      accepts only a still-unfinished attempt.
    steps: Reconciliation closes an attempt whose job never completed.
    expected: >-
      Read the failed standing and inspect the associated changes: record
      internal failure; reopen its eligible plan.
    negative: true
    data_needs: >-
      Fixtures for queued, the guard and the affected records; a fixed clock for
      time-dependent changes.
    source: >-
      services-crm:modules/merges/services/jobs/record-merge-job.ts:markMergeFailedForLostJob
    design_sources:
      - STATE-CRM-DQ-005
    note: >-
      The design supplies this transition obligation. A runtime binding requires
      assertions for its guard, destination and associated writes in one
      sequence.
    bound_to: []
    provenance: proposed
    execution_sources: []
  - id: ATS-CRM-DQ-016-23
    title: >-
      Observe running becoming failed after workflow failure handling or
      reconciliation settles unfinished execution
    category: transition
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-05
      - INV-DOM-CRM-DQ-004-14
    transition:
      model: STATE-CRM-DQ-005
      index: 5
      from: running
      to: failed
      guard: The attempt is queued or running when settlement obtains it.
      side_effects:
        - preserve existing executor failure or record internal failure
        - reopen its eligible plan
    preconditions: >-
      Arrange running standing with the transition guard satisfied: The attempt
      is queued or running when settlement obtains it.
    steps: Workflow failure handling or reconciliation settles unfinished execution.
    expected: >-
      Read the failed standing and inspect the associated changes: preserve
      existing executor failure or record internal failure; reopen its eligible
      plan.
    negative: true
    data_needs: >-
      Fixtures for running, the guard and the affected records; a fixed clock
      for time-dependent changes.
    source: >-
      services-crm:modules/merges/services/merges/merge-settlement.ts:settleMergeAsFailed
    design_sources:
      - STATE-CRM-DQ-005
    note: >-
      The design supplies this transition obligation. A runtime binding requires
      assertions for its guard, destination and associated writes in one
      sequence.
    bound_to: []
    provenance: proposed
    execution_sources: []
  - id: ATS-CRM-DQ-016-24
    title: An unanswered required conflict is identified on refusal
    category: invariant
    level: api
    proves:
      - INV-DOM-CRM-DQ-003-08
    preconditions: A preview with a required unanswered conflict.
    steps: Submit execution without answering it.
    expected: The response names the still-open conflict and queues no merge.
    negative: false
    data_needs: >-
      Records, versions and caller contexts owned by the run; transaction
      failure injection when the invariant concerns rollback.
    bound_to:
      - TST-CRM-DQ-183
    source: >-
      services-crm:modules/merges/tests/e2e/merges.e2e.spec.js#names the
      conflict that is still open, so a console can take the reader to it
    design_sources:
      - DOM-CRM-DQ-003
    execution_sources:
      - >-
        services-crm:modules/merges/tests/e2e/merges.e2e.spec.js#names the
        conflict that is still open, so a console can take the reader to it
    provenance: test
  - id: ATS-CRM-DQ-016-25
    title: An omitted client hash cannot bypass stale approval
    category: invariant
    level: api
    proves:
      - INV-DOM-CRM-DQ-003-09
    preconditions: A reviewed plan followed by changed dependent work.
    steps: Submit execution without a client fingerprint.
    expected: >-
      The service still rejects the stale stored review and returns its changed
      material.
    negative: false
    data_needs: >-
      Records, versions and caller contexts owned by the run; transaction
      failure injection when the invariant concerns rollback.
    bound_to:
      - TST-CRM-DQ-181
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/approval-binding.integration.spec.js#refuses
      an execution that submits no hash too, because the stored plan is the one
      last shown
    design_sources:
      - DOM-CRM-DQ-003
    execution_sources:
      - >-
        services-crm:modules/merges/tests/integration/services/merges/approval-binding.integration.spec.js#refuses
        an execution that submits no hash too, because the stored plan is the
        one last shown
    provenance: test
  - id: ATS-CRM-DQ-016-26
    title: A renamed display label does not change approval material
    category: invariant
    level: api
    proves:
      - INV-DOM-CRM-DQ-003-10
    preconditions: A preview with a named lookup value and its material hash captured.
    steps: Rename the lookup label and replan.
    expected: The display changes while the material hash stays equal.
    negative: false
    data_needs: >-
      Records, versions and caller contexts owned by the run; transaction
      failure injection when the invariant concerns rollback.
    bound_to:
      - TST-CRM-DQ-181
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/lookup-labels.integration.spec.js#answers
      the same material hash, a name being no part of what staff are approving
    design_sources:
      - DOM-CRM-DQ-003
    execution_sources:
      - >-
        services-crm:modules/merges/tests/integration/services/merges/lookup-labels.integration.spec.js#answers
        the same material hash, a name being no part of what staff are approving
    provenance: test
  - id: ATS-CRM-DQ-016-27
    title: Simultaneous submissions return the same attempt
    category: invariant
    level: api
    proves:
      - INV-DOM-CRM-DQ-004-01
    preconditions: Two execution requests for one ready plan.
    steps: Submit both concurrently and compare their returned merge identities.
    expected: Both responses identify one merge and only one creates it.
    negative: false
    data_needs: >-
      Records, versions and caller contexts owned by the run; transaction
      failure injection when the invariant concerns rollback.
    bound_to:
      - TST-CRM-DQ-181
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/merge-settlement.integration.spec.js#answers
      both requests the same merge
    design_sources:
      - DOM-CRM-DQ-004
    execution_sources:
      - >-
        services-crm:modules/merges/tests/integration/services/merges/merge-settlement.integration.spec.js#answers
        both requests the same merge
    provenance: test
  - id: ATS-CRM-DQ-016-28
    title: An attempt cannot absorb its own survivor
    category: invariant
    level: api
    proves:
      - INV-DOM-CRM-DQ-004-02
    preconditions: A direct merge row with the survivor included among absorbed records.
    steps: Attempt the database insertion.
    expected: The database refuses the invalid participant set.
    negative: false
    data_needs: >-
      Records, versions and caller contexts owned by the run; transaction
      failure injection when the invariant concerns rollback.
    bound_to: []
    source: >-
      services-crm:modules/merges/db/record-merges.table.ts:record_merges_merged_ids_check
    design_sources:
      - DOM-CRM-DQ-004
    execution_sources: []
    provenance: proposed
  - id: ATS-CRM-DQ-016-29
    title: Terminal outcomes require their completion stamps
    category: invariant
    level: api
    proves:
      - INV-DOM-CRM-DQ-004-03
    preconditions: Direct rows with missing completion time or a mismatched failure code.
    steps: Attempt successful and failed rows with each incomplete terminal shape.
    expected: The database rejects the incomplete outcomes.
    negative: false
    data_needs: >-
      Records, versions and caller contexts owned by the run; transaction
      failure injection when the invariant concerns rollback.
    bound_to: []
    source: >-
      services-crm:modules/merges/db/record-merges.table.ts:record_merges_failure_check
    design_sources:
      - DOM-CRM-DQ-004
    execution_sources: []
    provenance: proposed
  - id: ATS-CRM-DQ-016-30
    title: A stale-under-lock merge leaves the late task unmoved
    category: invariant
    level: api
    proves:
      - INV-DOM-CRM-DQ-004-04
    preconditions: A reviewed plan and a task added before locked execution replans.
    steps: Execute and read the task’s owner after refusal.
    expected: >-
      The merge fails as stale and the task still belongs to its original
      contact.
    negative: false
    data_needs: >-
      Records, versions and caller contexts owned by the run; transaction
      failure injection when the invariant concerns rollback.
    bound_to:
      - TST-CRM-DQ-181
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/approval-binding.integration.spec.js#fails
      the merge Stale inside its transaction rather than moving a task nobody
      approved
    design_sources:
      - DOM-CRM-DQ-004
    execution_sources:
      - >-
        services-crm:modules/merges/tests/integration/services/merges/approval-binding.integration.spec.js#fails
        the merge Stale inside its transaction rather than moving a task nobody
        approved
    provenance: test
  - id: ATS-CRM-DQ-016-31
    title: Competing plans cannot both absorb their shared contact
    category: invariant
    level: api
    proves:
      - INV-DOM-CRM-DQ-004-05
    preconditions: Two ready plans sharing one participant.
    steps: Execute both concurrently and read each outcome.
    expected: >-
      Exactly one merge succeeds; the competing attempt reports the absorbed
      participant.
    negative: false
    data_needs: >-
      Records, versions and caller contexts owned by the run; transaction
      failure injection when the invariant concerns rollback.
    bound_to:
      - TST-CRM-DQ-181
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/overlapping-merges.integration.spec.js#lets
      exactly one of the two merges happen
    design_sources:
      - DOM-CRM-DQ-004
    execution_sources:
      - >-
        services-crm:modules/merges/tests/integration/services/merges/overlapping-merges.integration.spec.js#lets
        exactly one of the two merges happen
    provenance: test
  - id: ATS-CRM-DQ-016-32
    title: Record history names the requester and merge destination
    category: invariant
    level: api
    proves:
      - INV-DOM-CRM-DQ-004-11
    preconditions: A successfully merged contact with captured audit entries.
    steps: Read the participant’s merge pointer.
    expected: 'The pointer identifies the requester, original contact, survivor and time.'
    negative: false
    data_needs: >-
      Records, versions and caller contexts owned by the run; transaction
      failure injection when the invariant concerns rollback.
    bound_to:
      - TST-CRM-DQ-181
    source: >-
      services-crm:modules/merges/tests/integration/services/merges/merged-from-history.integration.spec.js#says
      who merged which record into which, and when: the merge pointer
    design_sources:
      - DOM-CRM-DQ-004
    execution_sources:
      - >-
        services-crm:modules/merges/tests/integration/services/merges/merged-from-history.integration.spec.js#says
        who merged which record into which, and when: the merge pointer
    provenance: test
  - id: ATS-CRM-DQ-016-33
    title: A committed contact merge reaches its subscriber
    category: invariant
    level: api
    proves:
      - INV-DOM-CRM-DQ-004-12
    preconditions: A subscriber queue and a successful two-contact merge.
    steps: Run the merge and deliver the committed business event.
    expected: >-
      One subscriber message identifies the retained contact and absorbed
      identities.
    negative: false
    data_needs: >-
      Records, versions and caller contexts owned by the run; transaction
      failure injection when the invariant concerns rollback.
    bound_to:
      - TST-CRM-DQ-183
    source: >-
      services-crm:modules/merges/tests/e2e/business-events.e2e.spec.js#hands
      the subscriber the envelope of crm.contact.merged, about the survivor, in
      the merge’s tenant
    design_sources:
      - DOM-CRM-DQ-004
    execution_sources:
      - >-
        services-crm:modules/merges/tests/e2e/business-events.e2e.spec.js#hands
        the subscriber the envelope of crm.contact.merged, about the survivor,
        in the merge’s tenant
    provenance: test
  - id: ATS-CRM-DQ-016-34
    title: Repeated submission cannot create another job
    category: invariant
    level: api
    proves:
      - INV-DOM-CRM-DQ-004-13
    preconditions: A queued merge with its durable job already created.
    steps: Submit the same merge job again and inspect the root and step rows.
    expected: One job and one set of its watched steps remain.
    negative: false
    data_needs: >-
      Records, versions and caller contexts owned by the run; transaction
      failure injection when the invariant concerns rollback.
    bound_to: []
    source: >-
      services-crm:modules/merges/db/record-merge-jobs.table.ts:record_merge_jobs_merge_uidx,
      record_merge_jobs_customer_id_check;
      modules/merges/services/merges/merge-plans.ts:queueTheMergeOfThisPlan
    design_sources:
      - DOM-CRM-DQ-004
    execution_sources: []
    provenance: proposed
  - id: ATS-CRM-DQ-016-35
    title: Business refusal is settled instead of retried as transport failure
    category: invariant
    level: api
    proves:
      - INV-DOM-CRM-DQ-004-14
    preconditions: A participant refusal and a separate transient task exception.
    steps: >-
      Execute the workflow with each failure and inspect the task retry and
      terminal handling.
    expected: >-
      The refusal produces the settled failed attempt; only the eligible
      transient task exception enters the retry path.
    negative: false
    data_needs: >-
      Records, versions and caller contexts owned by the run; transaction
      failure injection when the invariant concerns rollback.
    bound_to: []
    source: >-
      services-crm:modules/merges/services/jobs/record-merge-job.ts:recordMergeWorkflow
    design_sources:
      - DOM-CRM-DQ-004
    execution_sources: []
    provenance: proposed
  - id: ATS-CRM-DQ-016-36
    title: Retry distinguishes transient task failure from refusal
    category: rule
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-11
    preconditions: >-
      One ready merge with an injected transient task error and another with a
      refusing participant.
    steps: Run each workflow and inspect the retry attempts and settlement.
    expected: >-
      Only the eligible task error is retried; the refusal is recorded as a
      business failure.
    negative: true
    data_needs: Run-owned records and caller permissions that distinguish the two cases.
    source: >-
      services-crm:modules/merges/services/jobs/record-merge-job.ts:recordMergeWorkflow
    design_sources:
      - CAP-CRM-DQ-016
    bound_to: []
    provenance: proposed
    execution_sources: []
  - id: ATS-CRM-DQ-016-37
    title: Confirmation and polling retain a readable execution outcome
    category: rule
    level: browser
    proves:
      - BR-CAP-CRM-DQ-016-14
    preconditions: >-
      A ready plan with dropped values, a delayed execution and an
      administrator.
    steps: >-
      Open confirmation, inspect participant labels and irreversibility,
      acknowledge the dropped values, submit and advance the clock beyond thirty
      seconds; leave and return.
    expected: >-
      The confirmation identifies what is kept and absorbed, and polling changes
      from one-second to five-second intervals; the result remains available
      after returning.
    negative: true
    data_needs: Run-owned records and caller permissions that distinguish the two cases.
    source: >-
      react-console:acceptance/crm/playwright/journeys/merging/CRM-ACC-0253.spec.ts#CRM-ACC-0253
    design_sources:
      - CAP-CRM-DQ-016
    bound_to: []
    provenance: proposed
    execution_sources: []
  - id: ATS-CRM-DQ-016-38
    title: A completed organization merge agrees with aliases and history
    category: interaction
    level: api
    proves:
      - BR-CAP-CRM-DQ-016-01
      - BR-CAP-CRM-DQ-016-02
      - BR-CAP-CRM-DQ-016-03
      - BR-CAP-CRM-DQ-016-04
      - BR-CAP-CRM-DQ-016-05
      - BR-CAP-CRM-DQ-016-06
      - BR-CAP-CRM-DQ-016-07
      - BR-CAP-CRM-DQ-016-08
      - BR-CAP-CRM-DQ-016-09
      - BR-CAP-CRM-DQ-016-10
      - BR-CAP-CRM-DQ-016-12
      - BR-CAP-CRM-DQ-016-13
      - BR-CAP-CRM-DQ-016-15
      - BR-CAP-CRM-DQ-016-11
      - BR-CAP-CRM-DQ-016-14
    exercises:
      - CAP-CRM-DQ-016
      - CAP-CRM-DQ-017
      - CAP-CRM-DQ-018
      - CAP-CRM-DQ-019
    workflow_sources:
      - WF-CRM-DQ-006
      - WF-CRM-DQ-007
    preconditions: >-
      Run-owned contact and organization records, the relevant staff permissions
      and the related state described by the sequence.
    steps: >-
      Approve and execute an organization merge, read the surviving
      affiliations, follow every absorbed identity and open the recorded
      outcome.
    expected: >-
      The successful attempt, alias destinations and retained history describe
      the same committed change.
    negative: false
    data_needs: >-
      An isolated workspace with related records and fixed timestamps; owned
      participant failure injection where requested.
    source: >-
      CAP-CRM-DQ-016; CAP-CRM-DQ-017; CAP-CRM-DQ-018; CAP-CRM-DQ-019;
      WF-CRM-DQ-006; WF-CRM-DQ-007
    note: >-
      This cumulative seam scenario remains proposed until one executable
      sequence establishes all of its outcomes.
    bound_to: []
    provenance: proposed
    workflow_coverage_note: >-
      The workflows identify the handoffs under review. Separate assertions
      leave recovery and failure ordering unproved; the capability coverage
      finding records that limit.
    execution_sources: []
evidence:
  - repository: services-crm
    source_sha: a8d1364f1dd44b723bb5f9acba12f983e9ec8d69
    paths:
      - modules/merges/services/planning/merge-engine.ts
      - modules/merges/tests/e2e/business-events.e2e.spec.js
      - modules/merges/tests/e2e/merges.e2e.spec.js
      - >-
        modules/merges/tests/integration/db/record-merges.table.integration.spec.js
      - >-
        modules/merges/tests/integration/services/jobs/job-reconciliation.integration.spec.js
      - >-
        modules/merges/tests/integration/services/merges/approval-binding.integration.spec.js
      - >-
        modules/merges/tests/integration/services/merges/lookup-labels.integration.spec.js
      - >-
        modules/merges/tests/integration/services/merges/merge-execution.integration.spec.js
      - >-
        modules/merges/tests/integration/services/merges/merge-settlement.integration.spec.js
      - >-
        modules/merges/tests/integration/services/merges/merged-from-history.integration.spec.js
      - >-
        modules/merges/tests/integration/services/merges/overlapping-merges.integration.spec.js
      - >-
        modules/merges/tests/integration/services/merges/toy-participant.integration.spec.js
      - modules/merges/tests/unit/services/planning/long-running-merge.spec.js
      - modules/merges/tests/unit/services/planning/merge-decisions.spec.js
      - >-
        modules/merges/tests/unit/services/planning/survivor-recommendation.spec.js
    note: >-
      Bindings identify authored proof; empty bindings remain proposed and
      findings record known limitations.
coverage:
  rule: covered
  transition: covered
  validation: covered
  permission: 'gap: FND-CRM-DQ-067'
  edge: 'gap: FND-CRM-DQ-067'
  failure: covered
  boundary: covered
  concurrency: covered
  invariant: covered
  interaction: covered
coverage_notes:
  permission: >-
    No complete scenario currently isolates this category; the finding lists the
    remaining proof obligation.
  edge: >-
    No complete scenario currently isolates this category; the finding lists the
    remaining proof obligation.
permission_coverage:
  - key: crm.contacts.merge
    scenario_ids: []
    finding: FND-CRM-DQ-067
  - key: crm.organizations.merge
    scenario_ids: []
    finding: FND-CRM-DQ-067
  - key: crm.merges.read
    scenario_ids: []
    finding: FND-CRM-DQ-067
proof_matrix:
  - rule: BR-CAP-CRM-DQ-016-01
    scenarios:
      - ATS-CRM-DQ-016-01
      - ATS-CRM-DQ-016-15
      - ATS-CRM-DQ-016-38
  - rule: BR-CAP-CRM-DQ-016-02
    scenarios:
      - ATS-CRM-DQ-016-02
      - ATS-CRM-DQ-016-13
      - ATS-CRM-DQ-016-38
  - rule: BR-CAP-CRM-DQ-016-03
    scenarios:
      - ATS-CRM-DQ-016-03
      - ATS-CRM-DQ-016-38
  - rule: BR-CAP-CRM-DQ-016-04
    scenarios:
      - ATS-CRM-DQ-016-04
      - ATS-CRM-DQ-016-13
      - ATS-CRM-DQ-016-38
  - rule: BR-CAP-CRM-DQ-016-05
    scenarios:
      - ATS-CRM-DQ-016-05
      - ATS-CRM-DQ-016-15
      - ATS-CRM-DQ-016-19
      - ATS-CRM-DQ-016-22
      - ATS-CRM-DQ-016-23
      - ATS-CRM-DQ-016-38
  - rule: BR-CAP-CRM-DQ-016-06
    scenarios:
      - ATS-CRM-DQ-016-06
      - ATS-CRM-DQ-016-13
      - ATS-CRM-DQ-016-16
      - ATS-CRM-DQ-016-20
      - ATS-CRM-DQ-016-21
      - ATS-CRM-DQ-016-38
  - rule: BR-CAP-CRM-DQ-016-07
    scenarios:
      - ATS-CRM-DQ-016-07
      - ATS-CRM-DQ-016-13
      - ATS-CRM-DQ-016-38
  - rule: BR-CAP-CRM-DQ-016-08
    scenarios:
      - ATS-CRM-DQ-016-08
      - ATS-CRM-DQ-016-38
  - rule: BR-CAP-CRM-DQ-016-09
    scenarios:
      - ATS-CRM-DQ-016-09
      - ATS-CRM-DQ-016-38
  - rule: BR-CAP-CRM-DQ-016-10
    scenarios:
      - ATS-CRM-DQ-016-10
      - ATS-CRM-DQ-016-17
      - ATS-CRM-DQ-016-18
      - ATS-CRM-DQ-016-38
  - rule: BR-CAP-CRM-DQ-016-11
    scenarios:
      - ATS-CRM-DQ-016-36
      - ATS-CRM-DQ-016-38
  - rule: BR-CAP-CRM-DQ-016-12
    scenarios:
      - ATS-CRM-DQ-016-11
      - ATS-CRM-DQ-016-38
  - rule: BR-CAP-CRM-DQ-016-13
    scenarios:
      - ATS-CRM-DQ-016-12
      - ATS-CRM-DQ-016-38
  - rule: BR-CAP-CRM-DQ-016-14
    scenarios:
      - ATS-CRM-DQ-016-37
      - ATS-CRM-DQ-016-38
  - rule: BR-CAP-CRM-DQ-016-15
    scenarios:
      - ATS-CRM-DQ-016-14
      - ATS-CRM-DQ-016-38
interaction_coverage:
  related:
    - CAP-CRM-DQ-017
    - CAP-CRM-DQ-018
    - CAP-CRM-DQ-019
  workflow_sources:
    - WF-CRM-DQ-006
    - WF-CRM-DQ-007
  scenarios:
    - ATS-CRM-DQ-016-12
    - ATS-CRM-DQ-016-38
---

# Execute the approved merge atomically: Capability Test Specification

## Coverage

The rule matrix names the authored checks. A covered category means that a scenario exists; it does not report a passing execution. The coverage notes and findings identify missing checks, while execution sources retain the exact assertions inspected.

| Required Rule | Scenarios |
|---|---|
| `BR-CAP-CRM-DQ-016-01` | `ATS-CRM-DQ-016-01`, `ATS-CRM-DQ-016-15`, `ATS-CRM-DQ-016-38` |
| `BR-CAP-CRM-DQ-016-02` | `ATS-CRM-DQ-016-02`, `ATS-CRM-DQ-016-13`, `ATS-CRM-DQ-016-38` |
| `BR-CAP-CRM-DQ-016-03` | `ATS-CRM-DQ-016-03`, `ATS-CRM-DQ-016-38` |
| `BR-CAP-CRM-DQ-016-04` | `ATS-CRM-DQ-016-04`, `ATS-CRM-DQ-016-13`, `ATS-CRM-DQ-016-38` |
| `BR-CAP-CRM-DQ-016-05` | `ATS-CRM-DQ-016-05`, `ATS-CRM-DQ-016-15`, `ATS-CRM-DQ-016-19`, `ATS-CRM-DQ-016-22`, `ATS-CRM-DQ-016-23`, `ATS-CRM-DQ-016-38` |
| `BR-CAP-CRM-DQ-016-06` | `ATS-CRM-DQ-016-06`, `ATS-CRM-DQ-016-13`, `ATS-CRM-DQ-016-16`, `ATS-CRM-DQ-016-20`, `ATS-CRM-DQ-016-21`, `ATS-CRM-DQ-016-38` |
| `BR-CAP-CRM-DQ-016-07` | `ATS-CRM-DQ-016-07`, `ATS-CRM-DQ-016-13`, `ATS-CRM-DQ-016-38` |
| `BR-CAP-CRM-DQ-016-08` | `ATS-CRM-DQ-016-08`, `ATS-CRM-DQ-016-38` |
| `BR-CAP-CRM-DQ-016-09` | `ATS-CRM-DQ-016-09`, `ATS-CRM-DQ-016-38` |
| `BR-CAP-CRM-DQ-016-10` | `ATS-CRM-DQ-016-10`, `ATS-CRM-DQ-016-17`, `ATS-CRM-DQ-016-18`, `ATS-CRM-DQ-016-38` |
| `BR-CAP-CRM-DQ-016-11` | `ATS-CRM-DQ-016-36`, `ATS-CRM-DQ-016-38` |
| `BR-CAP-CRM-DQ-016-12` | `ATS-CRM-DQ-016-11`, `ATS-CRM-DQ-016-38` |
| `BR-CAP-CRM-DQ-016-13` | `ATS-CRM-DQ-016-12`, `ATS-CRM-DQ-016-38` |
| `BR-CAP-CRM-DQ-016-14` | `ATS-CRM-DQ-016-37`, `ATS-CRM-DQ-016-38` |
| `BR-CAP-CRM-DQ-016-15` | `ATS-CRM-DQ-016-14`, `ATS-CRM-DQ-016-38` |

## Interactions With Related Capabilities

Execute the two-contact combination. Approve and execute an organization merge, read the surviving affiliations, follow every absorbed identity and open the recorded outcome.

These sequences test the handoffs named in the interaction coverage record. A proposed sequence remains unbound until an executable run checks its combined outcome; component assertions alone leave that obligation open.
