Add a second WAN link and the tunnels come up, yet a file copy still stalls when one path wobbles. The links are healthy and the VPN processes are running; what is missing is a contract between the carrier and the tunnel. Several sockets do not automatically behave like one connection, and the application above them cannot tell the difference until delivery breaks. Each part of the contract maps to a failure you can test, which is what makes it useful.

Write that contract before choosing a product. It has four parts: the stream the VPN receives, how the carrier recovers missing data, which endpoint identity survives a path change, and how the whole thing behaves when a path fails.

The symptom: links are up, the session still breaks

A monitoring graph that shows both links up proves only that each path can carry traffic. It does not prove that the VPN sees one ordered stream, that a packet lost on one path is recovered on another, or that the peer still knows which session it is talking to. The rest of the contract covers what that graph cannot show.

When a transfer stalls, find out whether the carrier kept delivering on the surviving path. If the session dies while the second link is idle, the carrier never used it. If the session survives but data arrives out of order or duplicated, the carrier is moving packets without a connection-level contract. Timestamps on both sides usually make that clear.

That distinction decides the fix. A routing or policy problem needs a path selection change; a missing ordering and recovery layer needs a different transport, not a bigger buffer.

Guarantee one: a connection-level byte stream

If the VPN needs a reliable ordered stream, the carrier must identify byte ranges above the individual path. Each underlying TCP connection numbers only its own segments, so a receiver cannot reorder across paths using those numbers alone.

Multipath TCP is the standardized example. It presents one reliable byte stream while coordinating several TCP subflows, with data-level sequence mapping and acknowledgment. The application reads a stream, not whichever subflow happened to deliver a chunk first.

On Linux, MPTCP is opt-in per socket through IPPROTO_MPTCP. When negotiation cannot use multipath behavior, the documented fallback is ordinary TCP, which means the application may keep working over one path without ever using the second. Check which behavior the deployed socket actually negotiated rather than assuming the kernel setting applied.

Guarantee two: ordering, duplication and recovery

Paths with different delays and loss rates force the carrier to buffer, reorder and retransmit. The contract has to state how much buffering is allowed, what backpressure the application sees and which path carries a retransmission.

A path that stays connected but stops delivering is harder than a clean close. The carrier must detect it, move outstanding data and avoid waiting forever for a segment that will never arrive. A simple "both links are up" check does not cover this state.

Duplication needs its own rule. Sending the same payload on both paths can improve latency, but the receiver must suppress the copy before it reaches the VPN. IPsec anti-replay is optional per security association and checks sequence numbers; a duplication layer that reorders or replays packets can trip it or hide the problem until the tunnel drops.

Guarantee three: endpoint identity and path join

The peer needs a stable way to recognize the session when a new path appears. If each path is authenticated as a separate tunnel, the VPN may see two sessions rather than one. If the carrier joins paths under one session, it must define how the new path is authenticated and what happens to the old one.

Record which addresses and identifiers remain stable: the tunnel endpoint, the carrier session identifier and any proxy in between. A proxy adds another availability and trust boundary even when it never sees the protected payload.

This is also where policy lives. A path that joins from an unexpected network may be technically valid and still violate the intended trust model. Decide whether new paths are accepted automatically, require authentication or are refused.

Guarantee four: bounded behavior under failure

Test a complete path failure, not only a slow one. The surviving path should carry the session without unbounded memory growth, and recovery should not depend on a timer longer than the application can tolerate. When the failed path returns, the carrier must decide whether to rebalance or leave the flow where it is.

Set limits for buffering, retransmission and path count, then verify them under loss, reordering, duplication and delay imbalance. Aggregate bandwidth is the least interesting number here; delivery continuity and memory bounds are the contract.

Keep carrier recovery state separate from the VPN's cryptographic state. A custom reliability layer that replaces established authentication or encryption is not a shortcut, and reusing sequence numbers across layers is how replay protection and diagnostics become unreliable.

Accept the carrier with a test plan

Write the four guarantees as pass or fail checks: one ordered stream, defined recovery, stable session identity, bounded failure behavior. Run each check with one path degraded and then with one path removed.

A single successful file transfer through a path change does not prove continuous operation. Repeat the transfer while toggling the preferred path, and inspect both the carrier's view and the VPN's own counters. If the two disagree about which path carried the data, the contract is not observable yet.

Keep the signed-off matrix with the deployment. It tells the next engineer which behavior was promised, which path combinations were tested and which failure mode remains unsupported, without another round of guessing from link status lights.

Barruulee wal qabatan