siyuan-note/siyuan · error
missing query param [u]
Error message
missing query param [u]
What it means
parseForwardProxyParams handles SiYuan's forward-proxy endpoint. The target URL must be supplied as query param `u`, base64 (RawURLEncoding) encoded. When `u` is absent or empty the handler aborts with "missing query param [u]" before doing any network work.
Solutions
- Add the `u` query parameter containing base64.RawURLEncoding of the target URL string
- Ensure the value is RawURLEncoding (no padding, - and _ alphabet), not StdEncoding
- Reproduce the encoding the frontend uses (search forwardProxy in app/src) and mirror it in your client
Example fix
// before
fetch("/api/network/forwardProxy?url=https://example.com")
// after
const u = base64urlEncode("https://example.com");
fetch("/api/network/forwardProxy?u=" + u) Defensive patterns
Strategy: validation
Validate before calling
if (!params.u) throw new Error("forwardProxy requires the u query param (base64url of target URL)"); Try / catch
try {
await fetch("/api/network/forwardProxy?" + qs);
} catch (e) {
if (String(e.msg).includes("missing query param")) fixParamEncoding();
} Prevention
- Always build proxy requests through a helper that enforces the u param
- Keep a single base64url encoding utility shared by all callers
When it happens
Trigger: Calling a forward-proxy API route (e.g. /api/network/forwardProxy) without the `u` query parameter, or with `u=` empty.
Common situations: Hand-constructed curl/browser requests to the proxy endpoint; a client integration that forgot to encode the target URL; older plugin code written against a changed API surface.
Understand the failure class
Background: "missing required argument" and "the following required arguments were not provided": what required-argument errors mean and how to fix them — this error's family across 20 libraries.
Related errors
AI-assisted analysis of siyuan-note/siyuan@9f775e8a12 (2026-09-19).
Data as JSON: /api/errors/0f5786cfe8559a36.
Report an issue: GitHub.
Appendix: source
Thrown at kernel/api/network.go:338
dialer := util.SSRFSafeDialer(timeout)
client := req.C()
client.SetTimeout(timeout)
client.SetDial(dialer.DialContext)
client.SetRedirectPolicy(req.MaxRedirectPolicy(3))
return client
}
// parseForwardProxyParams decodes the `u` and `h` query parameters.
//
// Query params:
// - `u`: RawURLEncoding base64 of the target URL string.
// - `h`: RawURLEncoding base64 of a JSON object map[string][]string.
// - `timeout`: The timeout for the request in nanoseconds.
func parseForwardProxyParams(c *gin.Context) (parsedURL *url.URL, headers *http.Header, timeout time.Duration, err error) {
uParam := c.Query("u")
if uParam == "" {
err = fmt.Errorf("missing query param [u]")
return
}
uBytes, decErr := base64.RawURLEncoding.DecodeString(uParam)
if decErr != nil {
err = fmt.Errorf("decode [u] failed: %s", decErr.Error())
return
}
parsedURL, err = url.ParseRequestURI(string(uBytes))
if err != nil {
err = fmt.Errorf("parse [u] failed: %s", err.Error())
return
}
h := http.Header{}
headers = &h
hParam := c.Query("h")
if hParam != "" {
hBytes, decErr := base64.RawURLEncoding.DecodeString(hParam)View on GitHub (pinned to 9f775e8a12)