{"record":{"id":"1b93d9782900a563","repo":"vitejs/vite","slug":"port-port-is-already-in-use","errorCode":null,"errorMessage":"Port ${port} is already in use","messagePattern":"Port (.+?) is already in use","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"packages/vite/src/node/http.ts","lineNumber":274,"sourceCode":"  },\n): Promise<number> {\n  const { port: startPort, strictPort, host, logger } = serverOptions\n\n  if (startPort === 0) {\n    const port = await getAvailableEphemeralPort(host)\n    if (port == null) {\n      throw new Error('No available ephemeral port found')\n    }\n\n    const result = await tryBindServer(httpServer, port, host)\n    if (result.success) {\n      return port\n    }\n    if (result.error.code !== 'EADDRINUSE') {\n      throw result.error\n    }\n    // this can happen if the port was listened by other process between getAvailableEphemeralPort and tryBindServer\n    throw new Error(`Port ${port} is already in use`)\n  }\n\n  for (let port = startPort; port <= MAX_PORT; port++) {\n    // Pre-check port availability on wildcard addresses (0.0.0.0, ::)\n    // so that we avoid conflicts with other servers listening on all interfaces\n    const portAvailableOnWildcard = await isPortAvailable(port)\n\n    // If port is not available on a wildcard address but strictPort is set,\n    // we still try binding directly before giving up.\n    if (strictPort) {\n      const result = await tryBindServer(httpServer, port, host)\n      if (result.success) {\n        if (!portAvailableOnWildcard) {\n          logger.warn(\n            colors.yellow(\n              `Port ${port} is in use on a wildcard address, but ${host ?? 'localhost'}:${port} is available. ` +\n                `There may be another server running on a wildcard IP on port ${port}.`,\n            ),","sourceCodeStart":256,"sourceCodeEnd":292,"githubUrl":"https://github.com/vitejs/vite/blob/b4d66fee14d970f45b8a6f3d7d6aee73ca9b88ab/packages/vite/src/node/http.ts#L256-L292","documentation":"When binding the dev server's HTTP listener to a specific port, Vite iterates ports starting at server.port. If strictPort is true and that exact port is taken (EADDRINUSE), or if no port in the scan is free, it throws 'Port X is already in use'. For port 0 the same error covers the race between finding and binding an ephemeral port.","triggerScenarios":"Another process (often a previous Vite instance, a webpack-dev-server, or a system service) is already bound to the configured port. With strictPort: true Vite refuses to fall forward; without it, Vite scans upward and only errors if every port up to 65535 is busy.","commonSituations":"Hot-reload loops leaving zombie servers; running two dev tools on 3000/5173; Docker port-forward collisions; macOS AirPlay receiver occupying port 5000.","solutions":["Free the port: find the PID (lsof -i :PORT) and kill it.","Set strictPort: false so Vite picks the next free port automatically.","Change server.port to a known-free value, or use port: 0 for ephemeral allocation."],"exampleFix":"// before\nserver: { port: 5173, strictPort: true } // 5173 taken\n// after\nserver: { port: 5173, strictPort: false }","handlingStrategy":"try-catch","validationCode":"const net = require('net');\nfunction isPortFree(port, host) {\n  return new Promise((resolve) => {\n    const tester = net.createServer()\n      .once('error', () => resolve(false))\n      .once('close', () => resolve(true))\n      .listen(port, host, () => tester.close());\n  });\n}","typeGuard":null,"tryCatchPattern":"try {\n  await server.listen();\n} catch (e) {\n  if (/Port \\d+ is already in use/.test(String(e.message))) {\n    config.server.port = 0; // fall back to ephemeral\n    await server.listen();\n  } else throw e;\n}","preventionTips":["Pre-check the port with net.createServer before listen, or set server.port: 0.","Use strictPort: false in dev so Vite scans for the next free port.","Kill zombie dev servers before starting new ones (lsof / kill)."],"tags":["network","dev-server","port","eaddrinuse"],"backgroundTag":null,"analyzedSha":"b4d66fee14d970f45b8a6f3d7d6aee73ca9b88ab","analyzedAt":"2026-08-11T11:49:19.515Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}