shadow1ng/fscan · error

%s: %w (webscan_request_send_error)

Error message

%s: %w (webscan_request_send_error)

What it means

clustersend wraps any error from DoRequest that is NOT a transport error with the localized 'request send error' message (transport errors are silently treated as a failed probe instead). So this error means the HTTP request was constructed and attempted, but the client refused/failed to send it for a non-transport reason — e.g. context deadline/cancellation, invalid configuration of the request at send time, or client-level rejection.

Source

Thrown at webscan/lib/poc_executor.go:804

	newRequest, err := http.NewRequestWithContext(oReq.Context(), rule.Method, reqURL, strings.NewReader(rule.Body))
	if err != nil {
		return false, fmt.Errorf("%s: %w", i18n.GetText("webscan_http_request_error"), err)
	}
	defer func() { newRequest = nil }()

	// 设置请求头
	newRequest.Header = oReq.Header.Clone()
	for key, value := range rule.Headers {
		newRequest.Header.Set(key, value)
	}

	// 发送请求
	resp, err := DoRequest(newRequest, rule.FollowRedirects, session)
	if err != nil {
		if isTransportError(err) {
			return false, nil
		}
		return false, fmt.Errorf("%s: %w", i18n.GetText("webscan_request_send_error"), err)
	}

	// 更新响应到变量映射
	variableMap["response"] = resp

	// 执行搜索规则
	if rule.Search != "" {
		searchContent := GetHeader(resp.Headers) + string(resp.Body)
		result := doSearch(rule.Search, searchContent)

		if len(result) > 0 {
			// 将搜索结果添加到变量映射
			for key, value := range result {
				variableMap[key] = value
			}
		} else {
			return false, nil
		}

View on GitHub (pinned to 95cc12e753)

Solutions

  1. Inspect the wrapped cause: "context deadline exceeded" means raise the timeout on the context passed to the scan; "context canceled" means the scan was aborted upstream.
  2. If the target is legitimately slow, increase the session timeout or exclude the target.
  3. If you expect network failures to be skipped, verify isTransportError recognizes them — a custom wrapped error may be misclassified as non-transport and surfaced here.
  4. Retry the scan to distinguish transient conditions from deterministic request rejection.

Example fix

// before
ctx := context.Background()
send := DoRequest(...) // webscan_request_send_error: context deadline exceeded
// after
ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second)
defer cancel()
send := DoRequest(...)
Defensive patterns

Strategy: try-catch

Validate before calling

if _, ok := oReq.Context().Deadline(); !ok {
    var cancel context.CancelFunc
    oReq = oReq.WithContext(context.WithTimeout(oReq.Context(), 30*time.Second))
    defer cancel()
}

Try / catch

resp, err := DoRequest(newRequest, rule.FollowRedirects, session)
if err != nil {
    if isTransportError(err) {
        return false, nil // expected for unreachable hosts
    }
    if errors.Is(err, context.DeadlineExceeded) {
        log.Printf("target %s timed out, raising timeout", newRequest.URL)
        return false, nil
    }
    if errors.Is(err, context.Canceled) {
        return false, err // scan aborted, propagate
    }
    return false, fmt.Errorf("%s: %w", i18n.GetText("webscan_request_send_error"), err)
}

Prevention

When it happens

Trigger: DoRequest(newRequest, rule.FollowRedirects, session) returns an error where isTransportError(err) is false — typically context deadline exceeded (the shared oReq context timed out), context canceled (scan aborted), or a non-transport client failure.

Common situations: Scanning a slow host that exceeds the session/context timeout during brute-force mode; user cancels the scan mid-run and the shared context is canceled; a request with both body and conflicting settings rejected by the client transport configuration.

Understand the failure class

Background: Request timed out: what client-side request timeouts mean across libraries (Request timed out, TIMED_OUT, APITimeoutError) — this error's family across 39 libraries.

Related errors


AI-assisted analysis of shadow1ng/fscan@95cc12e753 (2026-09-06). Data as JSON: /api/errors/2873e2a371f77259. Report an issue: GitHub.