Start with a checkout method that contains if carrier == ... branches. Define the smallest policy contract that the order flow needs, move each calculation behind an implementation, and inject the choice at the application boundary.
Add tests with a deterministic fake policy and an integration test for a carrier adapter. Include the timeout case: an abstraction should not hide the fact that one implementation makes a remote call and can fail.
In your write-up, name the expected change that justifies the interface. If only one stable behavior exists, explain why the extra layer is still useful or remove it. The linked reference shows the Strategy shape; this exercise asks you to decide whether that shape fits the pressure in your own code.