{"record":{"id":"4cefb18a377eee55","repo":"GoogleContainerTools/skaffold","slug":"creating-listener-w","errorCode":null,"errorMessage":"creating listener: %w","messagePattern":"creating listener: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"pkg/skaffold/server/server.go","lineNumber":178,"sourceCode":"\t\teventV2.SaveLastLog(opts.LastLogFile)\n\n\t\treturn errors.New(errStr)\n\t}\n\tif err != nil {\n\t\treturn callback, fmt.Errorf(\"starting HTTP server: %w\", err)\n\t}\n\n\tif opts.EnableRPC && opts.RPCPort.Value() == nil && opts.RPCHTTPPort.Value() == nil {\n\t\tlog.Entry(context.TODO()).Warnf(\"started skaffold gRPC API on random port %d\", grpcPort)\n\t}\n\n\treturn callback, nil\n}\n\nfunc newGRPCServer(preferredPort int) (func() error, int, error) {\n\tl, port, err := listenPort(preferredPort)\n\tif err != nil {\n\t\treturn func() error { return nil }, 0, fmt.Errorf(\"creating listener: %w\", err)\n\t}\n\n\tlog.Entry(context.TODO()).Infof(\"starting gRPC server on port %d\", port)\n\n\ts := grpc.NewServer()\n\tsrv = &server{\n\t\tbuildIntentCallback:   func() {},\n\t\tdeployIntentCallback:  func() {},\n\t\tsyncIntentCallback:    func() {},\n\t\tdevloopIntentCallback: func() {},\n\t\tautoBuildCallback:     func(bool) {},\n\t\tautoSyncCallback:      func(bool) {},\n\t\tautoDeployCallback:    func(bool) {},\n\t\tautoDevloopCallback:   func(bool) {},\n\t}\n\tv2.Srv = &v2.Server{\n\t\tBuildIntentCallback:   func() {},\n\t\tDeployIntentCallback:  func() {},","sourceCodeStart":160,"sourceCodeEnd":196,"githubUrl":"https://github.com/GoogleContainerTools/skaffold/blob/a1189de023efc32d4b8e11f395acc678aa555011/pkg/skaffold/server/server.go#L160-L196","documentation":"Skaffold's `newGRPCServer` wraps any failure from `listenPort(preferredPort)` when opening the TCP listener for the gRPC debug/user server. It means the process could not bind to a port, so the gRPC server (used for port-forward and debugging hooks) cannot start. The wrapped underlying error (e.g. from net.Listen) identifies the real cause.","triggerScenarios":"Calling `Initialize` with a preferredPort that is already in use, restricted (ports <1024 without privileges), or on an interface that is unavailable, causing `listenPort` to fail for the preferred port and all fallback attempts.","commonSituations":"Running multiple skaffold dev sessions concurrently so the default port (e.g. 50051) is taken; a zombie skaffold process still holding the port; container/sandbox environments blocking port binding; port in the ephemeral range being auto-allocated elsewhere.","solutions":["Find and kill the process holding the port (lsof -i :<port> or netstat) or the stale skaffold process.","Start with a different --port / preferredPort value so listenPort can bind successfully.","Check you are not trying to bind a privileged port (<1024) without elevated permissions.","Inspect the wrapped error (%w) to confirm whether it is EADDRINUSE, EACCES, or a DNS/interface issue and fix accordingly."],"exampleFix":"// before\nskaffold dev --port 50051 // port already in use\n// after\nskaffold dev --port 50061 // pick a free port","handlingStrategy":"fallback","validationCode":"package main\n\nimport (\n  \"net\"\n  \"fmt\"\n)\n\nfunc portFree(port int) error {\n  l, err := net.Listen(\"tcp\", fmt.Sprintf(\"127.0.0.1:%d\", port))\n  if err != nil { return err }\n  return l.Close()\n}\n// call portFree(preferredPort) before invoking Initialize; pick another port on error","typeGuard":"func isAddrInUse(err error) bool {\n  return errors.Is(err, syscall.EADDRINUSE)\n}","tryCatchPattern":"port, cleanup, err := skaffoldServer.Initialize(...)\nif err != nil {\n  if strings.Contains(err.Error(), \"creating listener\") {\n    log.Printf(\"port unavailable: %v; retrying with a different port\", err)\n    // retry with preferredPort+1 or 0 (random port)\n  } else {\n    return err\n  }\n}","preventionTips":["Check port availability with net.Listen before starting skaffold servers.","Kill stale skaffold processes before starting a new dev session.","Avoid hardcoding the same port across concurrent dev sessions.","Log the wrapped cause (%w) to distinguish EADDRINUSE from EACCES."],"tags":["network","grpc","port-binding","go"],"backgroundTag":"port-already-in-use","analyzedSha":"a1189de023efc32d4b8e11f395acc678aa555011","analyzedAt":"2026-09-05T12:09:27.064Z","contentChangedAt":"2026-09-05T12:09:27.064Z","schemaVersion":2},"datasetVersion":"2026-09-12T17:17:11.597Z"}