
On Mon, Mar 29, 2010 at 9:18 AM, Jeremy Shaw
On Mon, Mar 29, 2010 at 8:47 AM, Michael Snoyman
wrote: Jeremy,
We'd been discussing the PathInfo class previously; I understand now what you're trying to achieve with it, but I think for a lot of use cases using a parser like that will be unnecesary. For those cases, I'd hate to introduce a parsec dependency, especially given the 2/3 split we're dealing with right now.
Well, parsec is in the haskell platform, so it's really a question of can be it implemented so that it works with both 2 and 3.
I know it's painful to split this up into even more packages, but we do you think of adding web-routes-parser?
I would consider it, but I don't understand how that would work...
So far you have been pretty unexcited about the parsing having a type similar to:
[String] -> (Either String a, [String])
because it is often 'unnecessary'. But the problem with, [String] -> (Either String a), is that, as far as I can tell, it won't work in the cases where it *is* necessary. And you can't simply switch to, [String] -> (Either String a, [String]), when that happens.. But perhaps I am missing something here..
The reason I'm unexcited is that I never would have dreamed of defining my routes that way. I don't feel like drawing out this point too much, because you clearly *would* define your routes that way. However, just to draw the distinction in how I would do things differently, I'll use an example of mine that you quoted earlier: instance Yesod PB where resources = [$mkResources| /: GET: indexHandler /entries/$entryId: GET: entry /entries/$entryId/$filename: GET: media /feed: GET: feed If I were to convert this to a datatype, it would be: data PBRoutes = Home | Entry String | File String String | Feed I simply wouldn't nest a datatype inside any of the constructors. I understand that you want to do this in some circumstances, but I would simply "duplicate" the parsing code for the Entry and File constructors, since I find that parsing code trivial. In particular: parsePB ["entries", eid] = Entry eid parsePB ["entries", eid, filename] = File eid filename I don't see a need for providing a sophisticated parser. Also, question about the Site datatype: Did we want the formatLink and
parseLink functions to work on [String] instead of String? I think I see advantages either way. Also, I'm not sure if I sent this previously, but I think the defaultPage function is redundant; that should probably be specified by 'parseLink ""'.
I will have to think about [String] vs String more. I don't want using Site to mean you have to use PathInfo, but switching to [String] wouldn't have that effect, and would mean that people would not have to worry about those pesky encoding issues. The only real use case I have for not using PathInfo is if you wanted to create a function like: gfromPathSegments :: (Data url) => PathInfo -> Either String url. And that can be done most easily if PathInfo = [String]. So I think I'll make that change. In the old code base, where there was no url encoding done by the library, it did not really make a difference.
Regarding defaultPage, not all methods of generating formatLink / parseLink lend themselves to handling "" very easily, so it seemed nice to have a single place that can add that case in, rather than add similar code to all the parsers.. Also, I think that I sometimes changes the landing page of my site. But I think I will make 'defaultPage' a Maybe value, and bill it as a way to 'override' where "" resolves to.
That sounds good.
I'll try to get started on porting the Yesod mkResources code over to
web-routes now.
awesome!
- jeremy
So, I've thought about the syntax for this, and I have this idea in mind. $(createRoutes MyRoutes [$parseRoutes| /: name: Home methods: [GET] /user/#userid: name: User methods: [GET, PUT, DELETE] /static: name: Static subsite: StaticRoutes dispatch: staticRoutes |]) This would generate a datatype: data MyRoutes = Home | User Integer | Static StaticRoutes Handler functions would be getHome, getUser, putUser, deleteUser. Static would be a pluggable subsite; I'd have to play around with the syntax of that a bit. Also, this will allow *any* type of application, not just wai (I want this to be as general as possible). Michael