# CounterParty Relations Facet

### CounterParty Relations Facet

The **CounterParty Relations Facet** manages the relationship lifecycle between PartyA traders and their PartyB market-maker counterparties.

All functions here are restricted to PartyA accounts. PartyBs cannot call any of them.

> **Key Concepts:**
>
> * **Binding:** A PartyA must explicitly bind to a specific PartyB before they can trade together. This is a deliberate opt-in relationship, not an open marketplace.
> * **Unbinding Cooldown:** Unbinding isn't instant. PartyA initiates the process, waits through a cooldown period, then completes it. This prevents sudden exits that could leave PartyB exposed on open positions.
> * **Instant Action Mode:** An optional mode a PartyA can activate that enables faster settlement paths. While active, certain balance operations (like transfers and deallocations) are blocked. Deactivating it is also time-delayed via a proposal step.
> * **Deactivation Cooldown:** Just as unbinding has a cooldown, deactivating instant action mode requires a proposal first, followed by a waiting period before the deactivation can be completed.

***

#### Overview

The facet covers two separate flows — the binding flow and the instant action flow:

**Binding flow:**

1. PartyA calls `bindToPartyB()` to establish a relationship with a specific PartyB
2. When ready to exit, PartyA calls `initiateUnbindingFromPartyB()` to start the cooldown
3. After the cooldown passes, `completeUnbindingFromPartyB()` finalizes the exit
4. If PartyA changes their mind during the cooldown, `cancelUnbindingFromPartyB()` reverts the initiation

**Instant action mode flow:**

1. PartyA calls `activateInstantActionMode()` to enable instant settlement
2. When they want to turn it off, `proposeToDeactivateInstantActionMode()` starts the time-delay
3. After the deactivation cooldown, `deactivateInstantActionMode()` completes the process

***

#### activateInstantActionMode()

Enables instant action mode for the calling PartyA. Once active, the account can use instant settlement paths, but certain balance operations — like `internalTransfer()`, `externalTransfer()`, and `deallocate()` — are blocked until the mode is deactivated.

**Function Signature:**

```solidity
function activateInstantActionMode()
    external
    onlyNotPartyB(msg.sender)
    whenInstantModeIsNotActive(msg.sender)
    whenPartyNotPaused(msg.sender);
```

***

#### proposeToDeactivateInstantActionMode()

Starts the time-delayed process of turning off instant action mode. The proposal records the current timestamp so that `deactivateInstantActionMode()` can enforce the cooldown. Instant mode remains active until the deactivation is completed.

**Function Signature:**

```solidity
function proposeToDeactivateInstantActionMode()
    external
    onlyNotPartyB(msg.sender)
    whenInstantModeIsActive(msg.sender)
    whenPartyNotPaused(msg.sender);
```

***

#### deactivateInstantActionMode()

Finalizes the deactivation of instant action mode, completing the two-step process that began with `proposeToDeactivateInstantActionMode()`. Can only succeed once the required cooldown period (set by `deactiveInstantActionModeCooldown` in the Control Facet) has elapsed since the proposal.

**Function Signature:**

```solidity
function deactivateInstantActionMode()
    external
    onlyNotPartyB(msg.sender)
    whenPartyNotPaused(msg.sender);
```

***

#### bindToPartyB()

Establishes a binding relationship between the calling PartyA and a specified PartyB. Once bound, the two parties can trade together. A PartyA can only be bound to one PartyB at a time — binding to a new one requires first completing an unbind from the current counterparty.

**Function Signature:**

```solidity
function bindToPartyB(address partyB)
    external
    onlyNotPartyB(msg.sender)
    whenPartyNotPaused(msg.sender);
```

**Parameters:**

* **partyB:** The address of the PartyB to bind to. The library validates that this is a registered and active PartyB.

***

#### initiateUnbindingFromPartyB()

Starts the unbinding process from the currently bound PartyB. This records the initiation timestamp and begins the cooldown. The relationship is still active during this period — the PartyA is not unbound until `completeUnbindingFromPartyB()` is called.

**Function Signature:**

```solidity
function initiateUnbindingFromPartyB()
    external
    onlyNotPartyB(msg.sender)
    whenPartyNotPaused(msg.sender);
```

***

#### completeUnbindingFromPartyB()

Finalizes the unbinding from the current PartyB after the cooldown period has elapsed. Once completed, the PartyA is free to bind to a different PartyB or operate unbound.

**Function Signature:**

```solidity
function completeUnbindingFromPartyB()
    external
    onlyNotPartyB(msg.sender)
    whenPartyNotPaused(msg.sender);
```

***

#### cancelUnbindingFromPartyB()

Revokes a pending unbinding request, keeping the current PartyA/PartyB relationship intact. Can only be called after `initiateUnbindingFromPartyB()` and before `completeUnbindingFromPartyB()`.

**Function Signature:**

```solidity
function cancelUnbindingFromPartyB()
    external
    onlyNotPartyB(msg.sender)
    whenPartyNotPaused(msg.sender);
```

***
