v2rayA/v2rayA · error

target not specified

Error message

target not specified

What it means

Client.Process implements proxy.Outbound: it takes the last outbound from the xray session context and, if that outbound's Target is not valid (no address/port), aborts with "target not specified". The TUIC outbound needs a concrete destination to dial, which is normally supplied by routing.

Source

Thrown at core/hint/proxy/tuic/outbound.go:126

	i := strings.LastIndex(addr, ":")
	if i < 0 {
		return addr, "", nil
	}
	host = addr[:i]
	port = addr[i+1:]
	// Strip brackets from IPv6.
	if len(host) >= 2 && host[0] == '[' && host[len(host)-1] == ']' {
		host = host[1 : len(host)-1]
	}
	return host, port, nil
}

// Process implements proxy.Outbound.
func (c *Client) Process(ctx context.Context, link *transport.Link, _ internet.Dialer) error {
	outbounds := xray_session.OutboundsFromContext(ctx)
	ob := outbounds[len(outbounds)-1]
	if !ob.Target.IsValid() {
		return errors.New("target not specified")
	}
	destination := ob.Target

	destAddr := fmt.Sprintf("%s:%d", destination.Address.String(), destination.Port.Value())

	conn, err := c.dialer.DialContext(ctx, "tcp", destAddr)
	if err != nil {
		return errors.New("tuic: failed to dial destination").Base(err)
	}
	defer conn.Close()

	postRequest := func() error {
		return xray_buf.Copy(link.Reader, xray_buf.NewWriter(outboundConnWriter(conn)))
	}
	getResponse := func() error {
		return xray_buf.Copy(xray_buf.NewReader(outboundConnReader(conn)), link.Writer)
	}

View on GitHub (pinned to 71e5442fc5)

Solutions

  1. Fix routing rules so requests reaching this outbound carry a valid destination.
  2. Verify the session with outbounds (including Target) is injected into the context before dispatching to the outbound.
  3. In tests, construct an outbound entry with a valid v2ray destination and put it in the context.

Example fix

// before
ctx := context.Background()
err := client.Process(ctx, link, dialer)

// after
outbounds := xray_session.AppendToContext(context.Background(), &xray_session.Outbound{Target: dest})
ctx = xray_session.ContextWithOutbounds(context.Background(), outbounds)
err := client.Process(ctx, link, dialer)
Defensive patterns

Strategy: validation

Validate before calling

obs := xray_session.OutboundsFromContext(ctx)
if len(obs) == 0 || !obs[len(obs)-1].Target.IsValid() {
    return errors.New("no valid target in context before Process")
}

Type guard

func hasValidTarget(ctx context.Context) bool {
    obs := xray_session.OutboundsFromContext(ctx)
    return len(obs) > 0 && obs[len(obs)-1].Target.IsValid()
}

Try / catch

if err := client.Process(ctx, link, dialer); err != nil {
    if strings.Contains(err.Error(), "target not specified") {
        // routing produced no destination; check routing rules
    }
    return err
}

Prevention

When it happens

Trigger: Calling Process with a context whose outbounds slice's last entry has an invalid Target — e.g. no routing rule matched, the outbound was invoked without a destination, or the session metadata was not attached to the context.

Common situations: Routing rules fall through to the TUIC outbound without a target; tests calling Process with a bare context lacking xray_session.OutboundsFromContext entries; misconfigured routing that drops destination info.

Related errors


AI-assisted analysis of v2rayA/v2rayA@71e5442fc5 (2026-09-05). Data as JSON: /api/errors/ff07589e0c389a02. Report an issue: GitHub.