# queryStringParameters not working with redirect on production

**URL:** <https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828>\
**Category:** Support\
**Tags:** netlify-dev-open-beta, lambda-functions, redirects\
**Created:** [September 29, 2019, 7:39pm UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828 "2019-09-29T19:39:09Z")\
**Posts on this page:** 16\
**Page:** 2

<div class="post-metadata">

**Author:** ![Dennis](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/dennis/32/34_2.png) [@Dennis](https://answers.netlify.com/u/Dennis)\
**Post date:** [December 29, 2020, 3:38pm UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/23 "2020-12-29T15:38:44Z")

</div>

Hi @jimniels,

Yea, I think that was due to the fact that the code that was enabling the pass-through was reverted but has since been re-fixed. Can you confirm that this is the case?

For some context, the [post](https://answers.netlify.com/t/changes-to-redirects-with-query-string-parameters-are-coming/23436) mentions the fix was re-deployed 8 days ago.

---

<div class="post-metadata">

**Author:** ![jimniels](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/jimniels/32/1165_2.png) [@jimniels](https://answers.netlify.com/u/jimniels)\
**Post date:** [December 29, 2020, 10:43pm UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/24 "2020-12-29T22:43:03Z")

</div>

@Dennis nope, still not working for me.

Just ran a rebuild of my site above. My build outputs my redirect, which looks like this:

```auto
3:35:39 PM: '/api/v1/search /.netlify/functions/api-v1-search?siteId=macos 200', 

```

You can see my rule is saying to redirect to another path with a hard-coded query param (i.e. `/path` to `/.netlify-fn?foo=bar`) but the query param is not showing up in the lambda.

You can test this at the preview build. Do a GET to:

`https://5febaf1576d34a0007ef33aa--macosicongallery.netlify.app/api/v1/search?name=swift`

It doesn’t work. You’ll see the `siteId` parameter is coming back from the lambda function as undefined. If you hard code it in the GET, it works:

`https://5febaf1576d34a0007ef33aa--macosicongallery.netlify.app/api/v1/search?name=swift&siteId=macos`

So the redirect is still not working. Or maybe I’m missing something?

---

<div class="post-metadata">

**Author:** ![jimniels](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/jimniels/32/1165_2.png) [@jimniels](https://answers.netlify.com/u/jimniels)\
**Post date:** [December 30, 2020, 4:15am UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/25 "2020-12-30T04:15:22Z")

</div>

I feel like I must be missing something really basic here?

All I’m doing is a redirect from a path to a new path with a (hard-coded) query string param.

```auto
/path/to/resource /redirect/path?with=query 200

```

How does that not work?

---

<div class="post-metadata">

**Author:** ![jimniels](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/jimniels/32/1165_2.png) [@jimniels](https://answers.netlify.com/u/jimniels)\
**Post date:** [January 8, 2021, 12:00am UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/27 "2021-01-08T00:00:54Z")

</div>

Following up with more context. Hoping @fool or @Dennis can help me out.

So I’ve been playing with this a bit more to try and figure it out. I’ve found that doing a regular _redirect_ rule works as expected. But using rewrites doesn’t work as I would expect.

Note: all of these examples are using my preview build at: [https://5ff7956eba84190008348a88--macosicongallery.netlify.app](https://5ff7956eba84190008348a88--macosicongallery.netlify.app)

## Redirects (301s)

Here’s the redirect rule in my `_redirects` file:

```auto
/netlify-support-test-no-200 /404.html?foo=bar

```

Because I didn’t specify a HTTP code, it uses a 301 and redirects the user from one path to another with the specified query params.

If I curl that resource, I can see I get a 301 redirect to the 404 page _with the query parameters_.

 ![Screen Shot 2021-01-07 at 4.31.25 PM](https://global.discourse-cdn.com/netlify/original/3X/3/6/364f425bd8bb45250e5e1a70b8e9e0e493fa03ee.png)

If I hit that URL in my browser – [`/netlify-support-test-no-200`](https://5ff7956eba84190008348a88--macosicongallery.netlify.app/netlify-support-test-no-200) – it redirects to the 404 page _with the query parameters in the URL bar_.

![Screen Shot 2021-01-07 at 4.19.04 PM](https://global.discourse-cdn.com/netlify/original/3X/b/3/b3d74ae1fbb8715d2fc7563a89004dea6ebb19f6.png)

Cool, that works just as expected.

## Rewrites and proxies (200s)

If I setup a URL to rewrite with a 200, then I don’t see the query parameters show up. Here’s the rule in my `_redirects` file:

```auto
/netlify-support-test /404.html?foo=bar 200

```

If I curl this resource, it returns a 200 with the contents of the 404 page. That makes sense:

 ![Screen Shot 2021-01-07 at 4.36.02 PM](https://global.discourse-cdn.com/netlify/original/3X/a/0/a042c083e6cfbe12482c584022cc5391e1108ea4.png)

If I hit it directly in my browser ([`/netlify-support-test`](https://5ff7956eba84190008348a88--macosicongallery.netlify.app/netlify-support-test)) I see the contents of the 404 page (same as the redirect above) but my browser’s URL doesn’t change (and doesn’t have the query params in it)

![Screen Shot 2021-01-07 at 4.24.22 PM](https://global.discourse-cdn.com/netlify/original/3X/2/e/2e03a400ee76259bfb9edbe9a46f70bc996d41f3.png)

That all makes sense. Because this is a rewrite, Netlify is making a request to the URL with the query params behind the scenes, so any query params are hidden from the URL bar and from the curl.

**But that request that’s happening behind the scenes isn’t working as expected**

I have one more rewrite rule setup. This one is designed to be a rewrite that points to a URL with query params. Here’s the rule:

```auto
/netlify-support-test-params /.netlify/functions/netlify-support-test?foo=bar 200

```

Note that this is pointing at a netlify (lambda) function with explicit query parameters. The lambda function’s code is really simple. It’s essentially echoing back the query parameters.

 ![Screen Shot 2021-01-07 at 4.45.14 PM](https://global.discourse-cdn.com/netlify/original/3X/b/7/b7715a5fad89f355f3ddfd6913cb88ad95368996.png)

So my expectation is that if I curl [`/netlify-support-test-params`](https://5ff7956eba84190008348a88--macosicongallery.netlify.app/netlify-support-test-params) I’ll get a 200 and it will echo back `{"query": {"foo": "bar"}`. But it does not. The lambda receives no query parameters:

 ![Screen Shot 2021-01-07 at 4.43.22 PM](https://global.discourse-cdn.com/netlify/original/3X/9/5/95e77dd29f8b1d8e10f3c20112e7c86524922484.png)

However, if I do include some query params myself in the request, it echoes those back. For example, if I curl [`/netlify-support-test-params?hello=world`](https://5ff7956eba84190008348a88--macosicongallery.netlify.app/netlify-support-test-params?hello=world), I get a 200 with `{"query":{"hello":"world"}}` echoed back to me:

 ![Screen Shot 2021-01-07 at 4.48.00 PM](https://global.discourse-cdn.com/netlify/original/3X/2/9/2904a3f41e19d4619af5c0b13309024433d09c5a.png)

## What gives?

Is my expectation incorrect here? It appears Netlify’s rewrites/proxy engine is not actually making a request with query params in tow. To restate:

**Given this rule:** `/path /rewrite?with=params 200`

**I expect** : a request to `/path` will result in Netlify making a request to `/rewrite?with=params` behind the scenes and then returning a 200 result to `/path`.

**But what I get** is that a request to `/path` results in, apparently, Netlify making a request to `/rewrite` _without any query params_ and returning a 200 result to `/path`.

---

<div class="post-metadata">

**Author:** ![jen](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/jen/32/6044_2.png) [@jen](https://answers.netlify.com/u/jen)\
**Post date:** [January 20, 2021, 10:33pm UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/29 "2021-01-20T22:33:38Z")

</div>

Hey there,  
We put this question to the team who works on our proxy and they explained that rewrites to functions work differently than rewrites to other paths. They suggested that you could accomplish what you want by grabbing the incoming path (`/.netlify/functions/netlify-support-test?foo=bar`) directly in your function using `event.path` and then parsing the param you’re interested in within your function. Sorry for the confusion here. Let us know if that solution would work for you.

---

<div class="post-metadata">

**Author:** ![jimniels](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/jimniels/32/1165_2.png) [@jimniels](https://answers.netlify.com/u/jimniels)\
**Post date:** [January 21, 2021, 3:10am UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/30 "2021-01-21T03:10:29Z")

</div>

> rewrites to functions work differently than rewrites to other paths

Well that’s interesting. That must be the source of my problem.

> They suggested that you could accomplish what you want by grabbing the incoming path…directly in your function using `event.path` and then parsing the param you’re interested in within your function.

That doesn’t work. Or maybe I’m misunderstanding the suggestion?

Let’s say I have the following redirect:

`/thing /.netlify/functions/thing?foo=bar 200`

If I do a GET to `/thing` that results in the invoked function’s `event.path` being `/thing`, which as I type that I guess makes sense in the context of function calls. Given that case, however, there are no query parameters present and **it appears impossible for a function call to know about its `/.netlify/functions/path` along with any query params that might be present, _unless you do a GET to it directly_.**

So—and I’m writing out loud here—it sounds like my expectation is completely wrong. Given the redirect above, I would expect a GET to `/thing` to proxy a call to the netlify function URL, which would result in the function having `even.path` be `/.netlify/functions/thing?foo=bar`, which I would then be able to parse. But that’s not how it’s working. The location that is being proxied to—the `/.netlify/...` url—is completely hidden from the invoked function.

Thus, from what I can tell in the implementation, **it seems impossible to add query string parameters to a redirect for a function call** , i.e. even given a hard-coded redirect of

`/path /.netlify/functions/path?foo=bar 200`

It’s impossible for the invoked function to know anything about `foo=bar`.

---

<div class="post-metadata">

**Author:** ![marcus](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/marcus/32/2651_2.png) [@marcus](https://answers.netlify.com/u/marcus)\
**Post date:** [January 27, 2021, 10:57am UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/31 "2021-01-27T10:57:47Z")

</div>

Hi!

I suggested the workaround of using the request path in the function, and I’ll try to explain it a bit better.

### Context

Yes, the `event.path` in a function will always be the path of the original incoming request.  
This is mostly legacy behaviour that was implemented like this once and we can’t really change it now without breaking people’s existing functions.

Primary use case: This means that you can use redirects to make Netlify invoke a function for any path. Great, right?

### Guessing your use case

I’m guessing what you want to do is rewrite to a function from different paths and pass some data along in the different redirects based on which rule was matched, so that the function can behave differently using that added context.  
Yes, this is where the redirects mechanism falls a bit short.

### Solution 1: Do the matching inside your function

Since our redirect mechanism is not able to provide you the data of which rule it matched, you could try to **match the original request in your function** to determine what it should do.

Example:

`_redirects`

```auto
/first-thing /.netlify/functions/the-only-function 200!
/second-thing /.netlify/functions/the-only-function 200!

```

`the-only-function.js`

```js
exports.handler = async function(event, context) {
    if (event.path === "/first-thing") {
        // do one thing
    } else if (event.path === "/second-thing") {
        // do the other thing
    } else {
        // return 400 status, because the function was invoked raw
    }
}

```

### Solution 2: Proxy headers hack

When you rewrite something you can [add custom proxy headers (click for docs)](https://docs.netlify.com/routing/redirects/rewrites-proxies/#custom-headers-in-proxy-redirects).

The same example solved using those:

`netlify.toml`

```toml
[[redirects]]
from = "/first-thing"
to = "/.netlify/functions/the-only-function"
status = 200
force = true
headers = {X-Variant = "first-thing"}

[[redirects]]
from = "/second-thing"
to = "/.netlify/functions/the-only-function"
status = 200
force = true
headers = {X-Variant = "second-thing"}

```

`the-only-function.js`

```js
exports.handler = async function(event, context) {
    if (event.headers["X-Variant"] === "first-thing") {
        // do one thing
    } else if (event.headers["X-Variant"] === "second-thing") {
        // do the other thing
    } else {
        // return 400 status, because the function was invoked raw
    }
}

```

Hope this helps you solve your specific issue!

---

<div class="post-metadata">

**Author:** ![jonsully](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/jonsully/32/15053_2.png) [@jonsully](https://answers.netlify.com/u/jonsully)\
**Post date:** [January 27, 2021, 3:09pm UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/32 "2021-01-27T15:09:35Z")

</div>

Greetings!

Wanted to chime in here too with another option that may make for some better flexibility — in addition to @marcus’s premise of having your rewrite/redirect _entry points_ being unique paths, e.g. `/first-thing` and `/second-thing`, you _can_ use query string parameters on the entry-point side of even a rewrite to a Function and those will be available within the Function.

Meaning I can have a rewrite of

`/only-thing /.netlify/functions/my-one-function 200!`

and send a request to `example.com/only-thing?image=the_big_one.jpg`

then my function’s `event.path` will be `/only-thing` and `event.queryStringParameters` will be `{ "image": "the_big_one.jpg" }`.

Just more options for you 🙂

–  
Jon

---

<div class="post-metadata">

**Author:** ![jimniels](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/jimniels/32/1165_2.png) [@jimniels](https://answers.netlify.com/u/jimniels)\
**Post date:** [January 28, 2021, 4:07pm UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/33 "2021-01-28T16:07:32Z")

</div>

Thanks for the feedback. Going to add some context for anybody who ends up here in the future.

## Clarifying My Misunderstanding

I can see now that my original confusion was around the redirect functionality _as it applies to functions_. To quote @Marcus

> a function will always be the path of the original incoming request

So if I have a redirect to a function like this:

```auto
/foo /.netlify/functions/bar?with=param 200

```

And I do a GET to `/foo`, the lambda will be involved with `event.path` as `foo`. Hard-coded query params in the rewrite don’t show up.

Honestly, now as I type it out, it makes sense. I had mistakenly assumed the function call would note its path as being its canonical URL (i.e. always the `/.netlify/functions/...`) rather than whatever path it was originally called at, which makes sense. I could see use cases on either side, but I would venture my case is the outlier.

## Solution to My Problem

What I need is some extra data about the environment. The suggestion from @Marcus for headers is more aligned with what I need.

The production host name contains a piece of information I need. When I call a function, that shows up in `event.headers.host`, so I can parse that and find the info I need. The problem there is that when I’m on `localhost` that piece of info is gone. So I need a solution for local testing. This is easy enough now to just hard-code. But in the future, I’ll probably look into a more dynamic solution. Something along the lines of the using a custom header, i.e. `X-My-Value`. The complexity there is that I need that value to be based on an env variable and it looks like you can use env variables in `netlify.toml` but [it requires extra complexity](https://docs.netlify.com/configure-builds/file-based-configuration/#inject-environment-variable-values).

Thanks everyone for the clarification!

---

<div class="post-metadata">

**Author:** ![verythorough](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/verythorough/32/4912_2.png) [@verythorough](https://answers.netlify.com/u/verythorough)\
**Post date:** [March 11, 2021, 3:50am UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/34 "2021-03-11T03:50:20Z")

</div>

Hey folks, I happened across an alternative workaround that might be helpful for some of you. It involves setting an additional redirect in front of the rewrite to the function.

For example, say you wanted to take a path like `/img/kitten.jpg?width=640` and send it to your `img-resizer` function with the filename and width passed in `event.queryStringParameters`.

You could first transform the path with a 301 redirect with placeholders:

```auto
/img/:filename width=:width /resized-img?file=:filename&w=:width&q=75 301

```

That rule changes `/img/kitten.jpg?w=640` to `/resized-img?file=kitten.jpg&width=640`. Note that I was able to do three things with this rule:

- converted part of the path to a query parameter
- changed the name of an existing parameter
- added an additional hard-coded parameter

Now you can pass that transformed path to the function endpoint:

```auto
/resized-img /.netlify/functions/img-resizer 200

```

There’s no need to specify the query parameters because they are passed to the function `event` automatically.

⚠ Note that while this second rule can be a `200` rewrite, the first one cannot. **The first rule must be a `301` (or `302`) redirect** because the URL has to change in order for the redirect parser to be triggered a second time.

Now, with those two rules in place, If I enter `https://my-site.netlify.app/img/kitten.jpg?width=640` into a browser address bar, the following will happen:

1. The address bar URL will change to

```auto
https://my-site.netlify.app/resized-img?file=kitten.jpg&w=640&q=75

```

2. My `img-resizer` will be invoked with the following values passed in the `event` parameter:

```auto
{
  path: '/resized-img',
  queryStringParameters: { file: 'kitten.jpg', q: '75', w: '640' },
  ... other values ...
}

```

3. When the `img-resizer` function finishes, it will return its result to the browser. (Presumably the function has been written to return a resized image. 😉 )

With this image example, it’s worth noting that the whole double-redirect thing doesn’t require the path to be entered in the browser address bar. It works with inline references in code, too. So if I had an `img` tag in my page, like

```auto
<img src="/img/kitten.jpg?width=640"/>

```

It will still return the result of the `img-resizer` function in that `img` tag. You could do the same thing with, for example, a json file request in client-side JavaScript.

---

<div class="post-metadata">

**Author:** ![jonsully](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/jonsully/32/15053_2.png) [@jonsully](https://answers.netlify.com/u/jonsully)\
**Post date:** [March 11, 2021, 4:05am UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/35 "2021-03-11T04:05:12Z")

</div>

Interesting! 🤔 @verythorough have you happened to check if the `fetch` api follows 301s by default so that this approach could be used for JS calls?

—  
Jon

---

<div class="post-metadata">

**Author:** ![marcus](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/marcus/32/2651_2.png) [@marcus](https://answers.netlify.com/u/marcus)\
**Post date:** [March 11, 2021, 10:40am UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/36 "2021-03-11T10:40:49Z")

</div>

The default redirect policy on `fetch` is `follow`.

> A `RequestRedirect` enum value, which can be one the following strings:
> 
> - `follow`
> - `error`
> - `manual`
> 
> If not specified when the request is created, it takes the default value of `follow` .

See [Request: redirect property - Web APIs | MDN](https://developer.mozilla.org/en-US/docs/Web/API/Request/redirect)

---

<div class="post-metadata">

**Author:** ![jonsully](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/jonsully/32/15053_2.png) [@jonsully](https://answers.netlify.com/u/jonsully)\
**Post date:** [March 11, 2021, 5:40pm UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/37 "2021-03-11T17:40:11Z")

</div>

Great! Seems like that may be a viable work-around! Thanks @verythorough 🙌🏻

---

<div class="post-metadata">

**Author:** ![Rektovski](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/rektovski/32/43364_2.png) [@Rektovski](https://answers.netlify.com/u/Rektovski)\
**Post date:** [November 27, 2022, 3:10pm UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/38 "2022-11-27T15:10:13Z")

</div>

My site is working on this link

> **[Shop API](https://shopotara.netlify.app/)**
>
> Web site created using create-react-app

but I cant use any other links after .app/

for example there must be

> **[Shop API](https://shopotara.netlify.app/)**
>
> Web site created using create-react-app

> **[Shop API](https://shopotara.netlify.app/customers)**
>
> Web site created using create-react-app

> **[Shop API](https://shopotara.netlify.app//customers/products/)**
>
> Web site created using create-react-app

> **[Shop API](https://shopotara.netlify.app/aboutus)**
>
> Web site created using create-react-app

non of them works.

---

<div class="post-metadata">

**Author:** ![hrishikesh](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/hrishikesh/32/74607_2.png) [@hrishikesh](https://answers.netlify.com/u/hrishikesh)\
**Post date:** [November 27, 2022, 5:58pm UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/39 "2022-11-27T17:58:15Z")

</div>

All the links are working as far as I can see.

> [@Rektovski](#):
>
> [Shop API](https://shopotara.netlify.app/customers)  
> [Shop API](https://shopotara.netlify.app/customers/products/)

These 2 are showing a blank page, most likely because your app is configured to be blank on that, as I can see all the scripts are loading and working fine.

> [@Rektovski](#):
>
> [Shop API](https://shopotara.netlify.app/aboutus)

This page appears to work fine.

---

<div class="post-metadata">

**Author:** ![Rektovski](https://sea1.discourse-cdn.com/netlify/user_avatar/answers.netlify.com/rektovski/32/43364_2.png) [@Rektovski](https://answers.netlify.com/u/Rektovski)\
**Post date:** [November 27, 2022, 6:15pm UTC](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828/40 "2022-11-27T18:15:50Z")

</div>

ah yes because i added now \_redirect file

file input

/\* index.html 200

and it works now

[Previous page](https://answers.netlify.com/t/querystringparameters-not-working-with-redirect-on-production/3828.md?page=1)
