-
Notifications
You must be signed in to change notification settings - Fork 152
gloo-histroy Support custom query decoder / encoder #362
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
What prevents you from pushing the query as: struct Query {
json_url: String
} The url will be |
Hey, I just now also have the same issue. I have a Query struct that is really simple, like this: #[derive(Serialize, Deserialize)]
struct Query {
pub query: Vec<Predicate>,
pub sort: Option<String>,
} And I get an error. I believe that the underlying issue for this is that It seems that the I already use this crate to decode my querys with axum. For that reason, the crate has an I would recommend one of two options:
I think this would bring quite some value to people using more advanced query parameters. However, this is a breaking change I believe. If you would like, I could draft up a PR with my idea for how it could look like, in a way that does not break existing code. Cheers and thanks for the work on this crate! Edit: Some more context for this, see here. The serde-urlencoded crate sticks very closely to the RFC. As such, it really only supports key-value data, for example |
@hamza1311 the answer from @xfbs is really on the point.
The string will be still again url encoded by @xfbs Thanks for the detail explanation I didn't know about |
@futursolo what are your thoughts on this? I'm thinking, maybe we should switch over @Roba1993, does |
@hamza1311 I tested the |
I think using I am also concerned about introduce non-standard features.
I think this is not only non-standard, but also contradicts with some of the more popular implementations:
If I pass Non-standard nested behaviour is also historically known to cause security concerns as it can deserialise to objects that can be interpreted by MongoDB. One can introduce injections with expressions like: In conclusion, I am in favour of keeping I think that's also why warp and Axum both use However, I think an api allowing pushing query as string may be introduced to accommodate more flexible non standard pattern. One can make a wrapper History / Location type with custom query str if they want to use non-standard serialiser / deserialiser by reading / writing the string representation. An API that allows a custom serialiser / deserialiser would also work but I am not sure how this would work without major internal change as we expect the history object to be the same for all browser / hash history. |
I agree with this. I do think that having some type-safe facility is essential. I think it makes sense to have an escape hatch for situations where none of the serde-powered encoding schemes work, but the main API should focus on being type-safe and, to some extent, "magic".
Some context here:
I do not disagree, that is a reasonable encoding for the query you have specified. The issue that you are overlooking is that with the current situation, if you tried to encode this query you would get a panic. If you pass this to
I think I don't quite follow. It should not be our concern how MongoDB designs their APIs. This is simply a crate which exposes functionality to set the browser's history state. How this functionality is used, and making sure that it used safely, is left up to the end user.
I believe that That being said, I am also a proponent for leaving Rather, my proposal is to turn to the type system to find a way to give users a choice of which encoding method they would like to use. I will be following this commend up with a PR shortly to demonstrate what I mean by this. I am confident that we can find a solution that is pluggable and future-proof. |
With the PR I just made, the default behaviour is preserved. So you can write something like this: #[derive(Serialize, Deserialize)]
struct Query {
pub name: String,
pub sort: Option<String>,
}
let query = Query {
name: "name".into(),
sort: None,
};
location.replace_with_query("path", &query)?; And it will work and use However, if you want to encode something more complex, you can do it like this: use gloo_history::query::Qs;
let query = Query {
name: "name".into(),
sort: None,
};
location.replace_with_query("path", &Qs(query))?; That use gloo_history::query::Raw;
location.replace_with_query("path", &Raw("name=value&other=xyz"))?; The same functionality exists for decoding queries as well: // uses serde_urlencoded
let query: MyType = location.query()?;
// uses serde_qs
let query: MyType = location.query::<Qs<MyType>>()?;
// get raw query (just use query_str() instead)
let query: String = location.query::<Raw<String>>()?; If you need a custom encoding or decoding strategy, you can manually implement the I believe that this is the most flexible approach, does not break existing code (with one hypothetical caveat, which I have explained in the PR). |
Fixed by #364 |
Summary
Allow custom query decoder / encoder to support advanced use-cases.
Motivation
WI have the problem, that I need to serialize and deserialize rust structs into the a query. This is done via serde and serde_json. For better readability and changeability of the url I want to use an own serializer / deserializer. In my example along the lines of jsonurl.org.
Detailed Explanation
Unfortunately I have not a clear idea of to implement this right now in gloo.
Drawbacks, Rationale, and Alternatives
Drawback could be a more complex API?
An alternative would also to implement a jsonurl.org behavior natively into gloo-history. But this is would not be completely HTML conform and would break existing links.
Unresolved Questions
I also tried to use jsonurl to create a query string and push that as query. But it's still getting serialized / deserialized with the default behavior...
The text was updated successfully, but these errors were encountered: