Queries can be dispatched by assigning a query
object containing key/vals to an action
, its payload
object or its meta
object.
You will never have to deal with
search
strings directly, unless of course you want to manually supply them to<Link />
as theto
prop. The recommended approach is to use action objects though.
The query
key would be solely allowed on the action
itself, but to support Flux Standard Actions we have to provide the alternate 2 strategies.
The recommended approach is to put it on the action
unless you're using FSAs, in which case it's up to you.
By the time actions reach your reducers (after they're transformed by the middleware), the query
will exist on actions at:
action.query
(only if you supplied it here)action.meta.query
(only if you supplied it here)action.payload.query
(only if you supplied it here)action.meta.location.current.query
(always)
The <Link />
component--if you supply a string for the to
prop--will put it on the meta
key. If you want it elsewhere, it's recommended anyway to generate your URLs by supplying actions, in which case where you put it will be respected.
The actual search string will only ever exist at:
action.meta.location.current.search
Using links, here is some examples of how to format these actions:
action.query:
<Link to={{ type: 'ANYTHING', payload: { key: val }, query: { foo: 'bar' } }}>
action.payload.query:
<Link to={{ type: 'ANYTHING', payload: { key: val, query: { foo: 'bar' } } }}>
action.meta.query:
<Link to={{ type: 'ANYTHING', payload: { key: val }, meta: { query: { foo: 'bar' } } }}>
The matching route would be:
const routesMap = {
ANYTHING: '/anything/:key'
}
Notice there is no path params for query key/vals. They don't affect the determination of which route is selected. Only the type
and payload
do. The same type
is shared no matter what query is provided..
Here:
store.getState().location.query
store.getState().location.search
To enable query string serialization you must provide a querySerializer
option to connectRoutes
like this:
import queryString from 'query-string'
connectRoutes(routesMap, {
querySerializer: queryString
})
If you would like to create your own, you can pass any object with a stringify
and parse
function. The former takes an object and creates a query string and the latter takes a string
and creates an object.
Also note that the query-string
package will produce strings for numbers. There's a package made for express that will format numbers into ints
, which you may be interested in learning from if you want to achieve that goal. I couldn't find a general one identical to this one. If you make it, publish it to NPM and make a PR to this doc with a link to it. I think it's a mistake that numbers aren't converted for you.
If you are using server side rendering you will need to make sure that connectRoutes
receives proper configuration object containing full req.path including query in initialEntries
.
With Express req.path
does not contain the query. In this case you need to use initialEntries: [req.originalUrl]
instead of initialEntries: [req.path]
or if your server of choice does not give you req.originalUrl
then manually append query string to recreate full path. E.g. (#56).
You can test out query support on codesandbox here: