{"record":{"id":"5d8ae012e2fe8e09","repo":"micro/go-micro","slug":"failed-to-start-agent-w","errorCode":null,"errorMessage":"failed to start agent: %w","messagePattern":"failed to start agent: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"critical","filePath":"agent/agent.go","lineNumber":634,"sourceCode":"\n\tserverOpts := []server.Option{\n\t\tserver.Name(a.opts.Name),\n\t\tserver.Address(a.opts.Address),\n\t\tserver.Registry(a.opts.Registry),\n\t\tserver.Metadata(map[string]string{\n\t\t\t\"type\":     \"agent\",\n\t\t\t\"services\": strings.Join(a.opts.Services, \",\"),\n\t\t}),\n\t}\n\tif a.opts.Broker != nil {\n\t\tserverOpts = append(serverOpts, server.Broker(a.opts.Broker))\n\t}\n\ta.server = server.NewServer(serverOpts...)\n\n\t_ = pb.RegisterAgentHandler(a.server, a)\n\n\tif err := a.server.Start(); err != nil {\n\t\treturn fmt.Errorf(\"failed to start agent: %w\", err)\n\t}\n\n\tstopCh := make(chan struct{})\n\ta.mu.Lock()\n\ta.stopCh = stopCh\n\ta.mu.Unlock()\n\n\tfmt.Printf(\"Agent %s registered (manages: %s)\\n\", a.opts.Name, strings.Join(a.opts.Services, \", \"))\n\n\t// Optionally serve the agent directly over the A2A protocol, calling\n\t// Ask in-process — no separate gateway needed to be queried by URL.\n\tif a.opts.A2AAddress != \"\" {\n\t\tcard := a2a.Card(a.opts.Name, \"http://localhost\"+a.opts.A2AAddress, \"\", a.opts.Services)\n\t\thandler := a2a.NewAgentStreamHandler(card, func(ctx context.Context, text string) (string, error) {\n\t\t\tresp, err := a.Ask(ctx, text)\n\t\t\tif err != nil {\n\t\t\t\treturn \"\", err\n\t\t\t}","sourceCodeStart":616,"sourceCodeEnd":652,"githubUrl":"https://github.com/micro/go-micro/blob/24529f140421a11a33b6999ab7944f2021cfd69c/agent/agent.go#L616-L652","documentation":"When starting the agent's embedded server (Run/serve path, agent/agent.go:634), server.Start() failures are wrapped as 'failed to start agent: %w'. This usually means the transport/port setup failed, so the agent never becomes callable.","triggerScenarios":"Calling the agent's run/serve entry point when the underlying micro server fails to start: port already in use, invalid transport/address options, or transport initialization errors.","commonSituations":"Port conflicts with another process, bad --address/transport flags or env config, missing permissions to bind the port, misconfigured TLS for the server transport.","solutions":["Read the wrapped error to identify the concrete server failure","Check that the configured address/port is free (lsof/netstat) and change it if taken","Validate server Options (transport, address, TLS settings) passed to the agent","Run with elevated privileges or a port >1024 if binding is permission-denied","Check for a stale previous instance still holding the port and stop it"],"exampleFix":"// before\nagent.Run(ctx) // binds :8080, fails: address in use\n// after\nsrvOpts := []server.Option{server.Address(\":8081\")}\nag := agent.New(..., agent.ServerOptions(srvOpts...))\nagent.Run(ctx)\n","handlingStrategy":"try-catch","validationCode":"// before starting, ensure the port is free\nln, err := net.Listen(\"tcp\", addr)\nif err != nil { return fmt.Errorf(\"address %s unavailable: %w\", addr, err) }\nln.Close()","typeGuard":null,"tryCatchPattern":"if err := ag.Run(ctx); err != nil {\n    if strings.Contains(err.Error(), \"failed to start agent\") {\n        log.Printf(\"agent server failed: %v\", errors.Unwrap(err))\n        // pick a different port or fix transport config, then restart\n    }\n    return err\n}","preventionTips":["Configure ports via config with collision checks at deploy time","Use dynamic/free ports in dev environments","Validate transport and TLS options before launch","Run a startup smoke test that binds the address before the agent does"],"tags":["go","server","startup","port-binding"],"backgroundTag":"address-already-in-use","analyzedSha":"24529f140421a11a33b6999ab7944f2021cfd69c","analyzedAt":"2026-09-01T02:52:24.923Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T05:18:18.240Z"}