{"record":{"id":"633b3abcdfd097ee","repo":"XTLS/Xray-core","slug":"failed-to-dispatch-request-to-destination","errorCode":null,"errorMessage":"failed to dispatch request to ${destination}","messagePattern":"failed to dispatch request to (.+?)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"proxy/trojan/server.go","lineNumber":334,"sourceCode":"\n\tif err := task.Run(ctx, requestDone); err != nil {\n\t\treturn err\n\t}\n\treturn nil\n}\n\nfunc (s *Server) handleConnection(ctx context.Context, sessionPolicy policy.Session,\n\tdestination net.Destination,\n\tclientReader buf.Reader,\n\tclientWriter buf.Writer, dispatcher routing.Dispatcher,\n) error {\n\tctx, cancel := context.WithCancel(ctx)\n\ttimer := signal.CancelAfterInactivity(ctx, cancel, sessionPolicy.Timeouts.ConnectionIdle)\n\tctx = policy.ContextWithBufferPolicy(ctx, sessionPolicy.Buffer)\n\n\tlink, err := dispatcher.Dispatch(ctx, destination)\n\tif err != nil {\n\t\treturn errors.New(\"failed to dispatch request to \", destination).Base(err)\n\t}\n\n\trequestDone := func() error {\n\t\tdefer timer.SetTimeout(sessionPolicy.Timeouts.DownlinkOnly)\n\t\tif buf.Copy(clientReader, link.Writer, buf.UpdateActivity(timer)) != nil {\n\t\t\treturn errors.New(\"failed to transfer request\").Base(err)\n\t\t}\n\t\treturn nil\n\t}\n\n\tresponseDone := func() error {\n\t\tdefer timer.SetTimeout(sessionPolicy.Timeouts.UplinkOnly)\n\n\t\tif err := buf.Copy(link.Reader, clientWriter, buf.UpdateActivity(timer)); err != nil {\n\t\t\treturn errors.New(\"failed to write response\").Base(err)\n\t\t}\n\t\treturn nil\n\t}","sourceCodeStart":316,"sourceCodeEnd":352,"githubUrl":"https://github.com/XTLS/Xray-core/blob/7d214f8b094f75322fa3990f8aadad1c912f24f5/proxy/trojan/server.go#L316-L352","documentation":"The routing dispatcher refused to open an outbound link for the destination requested by the trojan client (dispatcher.Dispatch failed). Dispatch resolves the destination through routing rules and dials the first outbound; failure means no route matched, the outbound errored, or the destination is invalid/unreachable.","triggerScenarios":"Routing rules send the destination to a tag that does not exist (balancer/strategy typo), the selected outbound fails to dial (freedom with blocked network, proxy outbound down), or the destination address is malformed (e.g. empty domain after client-side resolution).","commonSituations":"Config references an outbound tag removed in an edit; 'block' rule matched unintentionally; upstream proxy credentials expired; DNS failure inside dispatch.","solutions":["Check routing rules: does a rule with action 'block' or a bogus outboundTag match this destination","Verify the outboundTag in rules exists in outbounds and that outbound can dial (test it directly)","Look at the Base error in the log — it carries the dispatcher's own failure reason (e.g. 'failed to get outbound handler' or dial timeout)","If DNS inside dispatch fails, fix the configured DNS servers or use domainStrategy ipResolve on the outbound"],"exampleFix":"// json: make sure the tag referenced by rules exists\n\"routing\": {\"rules\": [{\"type\": \"field\", \"ip\": [\"geoip:private\"], \"outboundTag\": \"direct\"}]},\n\"outbounds\": [{\"tag\": \"direct\", \"protocol\": \"freedom\"}]","handlingStrategy":"validation","validationCode":"// before dispatching, sanity-check the destination shape\nfunc validDest(d net.Destination) bool {\n    return d.Port > 0 && d.Address != nil &&\n        (d.Network == net.Network_TCP || d.Network == net.Network_UDP)\n}","typeGuard":null,"tryCatchPattern":"link, err := dispatcher.Dispatch(ctx, destination)\nif err != nil {\n    errors.LogError(ctx, errors.New(\"failed to dispatch request to \", destination).Base(err))\n    return err // per-connection failure; do not crash the inbound\n}","preventionTips":["Validate config at startup: every outboundTag in routing rules must exist in outbounds","Add an explicit final direct/block rule so dispatch always has a valid target","Test outbounds independently after credential or server changes"],"tags":["trojan","dispatch","routing"],"backgroundTag":null,"analyzedSha":"7d214f8b094f75322fa3990f8aadad1c912f24f5","analyzedAt":"2026-08-15T14:26:24.325Z","schemaVersion":2},"datasetVersion":"2026-08-15T17:31:12.345Z"}