(attempts: FailedPortAttempt[])
| 827 | } |
| 828 | |
| 829 | function formatRandomPortUnavailableError(attempts: FailedPortAttempt[]): Error { |
| 830 | const blockingAttempts = attempts.filter((attempt) => !isOccupiedPort(attempt.result)); |
| 831 | |
| 832 | if (blockingAttempts.length > 0) { |
| 833 | const last = blockingAttempts[blockingAttempts.length - 1]; |
| 834 | return new Error( |
| 835 | `[browse] Cannot bind localhost ports after ${attempts.length} attempts in range ` + |
| 836 | `${RANDOM_PORT_MIN}-${RANDOM_PORT_MAX}. Last error: ${formatPortFailureDetail(last)}. ` + |
| 837 | `This usually means the current sandbox or OS permissions are blocking localhost port binding, ` + |
| 838 | `not that every sampled port is occupied. Allow localhost binding, set BROWSE_PORT to an approved ` + |
| 839 | `port, or run browse from an unrestricted terminal.` |
| 840 | ); |
| 841 | } |
| 842 | |
| 843 | return new Error( |
| 844 | `[browse] No available port after ${RANDOM_PORT_RETRIES} attempts in range ` + |
| 845 | `${RANDOM_PORT_MIN}-${RANDOM_PORT_MAX}; every sampled port was already in use` |
| 846 | ); |
| 847 | } |
| 848 | |
| 849 | // Test if a port is available by binding and immediately releasing. |
| 850 | // Uses net.createServer instead of Bun.serve to avoid a race condition |
no test coverage detected