hoppscotch/hoppscotch · error · Error

Query param key must be a string

Error message

Query param key must be a string

What it means

Thrown by pm.request.url.query.remove() when the key argument is not a string. The method compares each existing param's key against the supplied key, so a non-string would never match and would hide a no-op bug; the guard makes the misuse explicit.

Source

Thrown at packages/hoppscotch-js-sandbox/src/bootstrap-code/pre-request.js:603

          get: () => {
            return {
              // Basic manipulation methods
              add: (param) => {
                if (!param || !param.key)
                  throw new Error("Query param must have a 'key' property")
                const currentParsed = urlObj._parseUrl()
                currentParsed.queryParams.push({
                  key: param.key,
                  value: param.value || "",
                })
                globalThis.hopp.request.setUrl(
                  urlObj._rebuildUrl(currentParsed)
                )
              },

              remove: (key) => {
                if (typeof key !== "string")
                  throw new Error("Query param key must be a string")
                const currentParsed = urlObj._parseUrl()
                currentParsed.queryParams = currentParsed.queryParams.filter(
                  (p) => p.key !== key
                )
                globalThis.hopp.request.setUrl(
                  urlObj._rebuildUrl(currentParsed)
                )
              },

              upsert: (param) => {
                if (!param || !param.key)
                  throw new Error("Query param must have a 'key' property")
                const currentParsed = urlObj._parseUrl()
                const idx = currentParsed.queryParams.findIndex(
                  (p) => p.key === param.key
                )
                if (idx >= 0) {
                  currentParsed.queryParams[idx].value = param.value || ""

View on GitHub (pinned to 1acb8a3a75)

Solutions

  1. Pass the key as a string: query.remove('a').
  2. If you have an object, pass its key field: query.remove(obj.key).
  3. For multiple keys, use pm.request.url.removeQueryParams(['a','b']).

Example fix

// before
pm.request.url.query.remove(foundParam)

// after
pm.request.url.query.remove(foundParam.key)
Defensive patterns

Strategy: type-guard

Validate before calling

if (typeof key !== 'string') {
  throw new Error('query.remove requires a string key');
}

Type guard

function isStringKey(v) {
  return typeof v === 'string' && v.length > 0;
}

Try / catch

try {
  pm.request.url.query.remove(key);
} catch (e) {
  if (/must be a string/.test(e.message) && key && key.key) pm.request.url.query.remove(key.key);
  else throw e;
}

Prevention

When it happens

Trigger: Calling query.remove(123), query.remove({key:'a'}), query.remove(['a']), query.remove(undefined), or query.remove(null). Passing a param object instead of its key string is the most common form.

Common situations: Passing the whole param object from a each() callback instead of p.key; passing a numeric key; passing an array of keys (remove only takes one — use removeQueryParams for bulk).

Related errors


AI-assisted analysis of hoppscotch/hoppscotch@1acb8a3a75 (2026-08-12). Data as JSON: /api/errors/490bf1b1d3534a92. Report an issue: GitHub.