[cgiapp] Best practice for CGI errors
Hi I suspect the reason I can't fun the answer for this is that it is too obvious... but I am having a moment of doubt! If one wants to return an error to the client because they have not included the correct parameters for the CGI request, should one use one of the HTTP status codes and if so which one? And then is it ok/sensible to include an error message in the body? Or should success or failure at the app level be indicated solely in the body of the response, with the HTTP response codes only being used to indicate an HTTP error ie if they don't include the correct parameters for one's app but it is still a valid HTTP request then use 200 but have some error notification inside the response body. If this is the case is there any kind of standard practice? I should probably mention that I am not responding with HTML here but rather this is a simple API or 'web service' - however I was hoping to avoid using SOAP or the like as it is very simple and CGI style GET with the return value in the response body should work fine - just having a momentary quandary on the error issue. Any suggestions gratefully receieved! Cheers Mark # CGI::Application community mailing list #### ## To unsubscribe, or change your message delivery options, ## ## visit: http://www.erlbaum.net/mailman/listinfo/cgiapp## #### ## Web archive: http://www.erlbaum.net/pipermail/cgiapp/ ## ## Wiki: http://cgiapp.erlbaum.net/ ## ####
Re: [cgiapp] Best practice for CGI errors
Mark Knoop wrote: If one wants to return an error to the client because they have not included the correct parameters for the CGI request, should one use one of the HTTP status codes and if so which one? Generally I don't use the HTTP status codes unless there is an error on the HTTP level. So for HTTP redirection, general server problem, etc. But HTTP codes are not application specific codes. And then is it ok/sensible to include an error message in the body? For me application specific codes should be part of the application, so it's part of the response. Are you returning your response as structured data (XML, JSON, etc)? If so, I'd just define a part of the spec that lists your application specific error codes and what they mean. If your response is not structured data, then just put a human readable error in the response. -- Michael Peters Plus Three, LP # CGI::Application community mailing list #### ## To unsubscribe, or change your message delivery options, ## ## visit: http://www.erlbaum.net/mailman/listinfo/cgiapp## #### ## Web archive: http://www.erlbaum.net/pipermail/cgiapp/ ## ## Wiki: http://cgiapp.erlbaum.net/ ## ####
Re: [cgiapp] Best practice for CGI errors
Mark Knoop wrote: If one wants to return an error to the client because they have not included the correct parameters for the CGI request, should one use one of the HTTP status codes and if so which one? Generally I don't use the HTTP status codes unless there is an error on the HTTP level. So for HTTP redirection, general server problem, etc. But HTTP codes are not application specific codes. And then is it ok/sensible to include an error message in the body? For me application specific codes should be part of the application, so it's part of the response. Are you returning your response as structured data (XML, JSON, etc)? If so, I'd just define a part of the spec that lists your application specific error codes and what they mean. If your response is not structured data, then just put a human readable error in the response. -- Michael Peters Plus Three, LP Thanks Michael. I was going to have a single line of text in the response containing the method return value which was why I was wondering if there was another way of indicating an error (in which case I would use the response body for an error message). Of course it would be easy to include more info in the response - but then perhaps I should reconsider my approach re how to implement an RPC so ...while I am here (and acknowledging that this is slightly off topic but at the same time it is probably somehting that many of you have had much experience in 'real-world' scenarios) can I ask whether CGI::App users have any favourite ways to do it re 'web services' ie remote methods/apis that do something then return some data? SOAP, XML-RPC, bespoke XML/JSON/other in response to GET/POST with CGI params, any other approach? My methods and responses are very simple. It would be nice to have hassle free security already there - this was the one advantage to SOAP - the main disadvantage being a lack of understanding on my part... Cheers Mark # CGI::Application community mailing list #### ## To unsubscribe, or change your message delivery options, ## ## visit: http://www.erlbaum.net/mailman/listinfo/cgiapp## #### ## Web archive: http://www.erlbaum.net/pipermail/cgiapp/ ## ## Wiki: http://cgiapp.erlbaum.net/ ## ####
Re: [cgiapp] Best practice for CGI errors
Mark Knoop wrote: ...while I am here (and acknowledging that this is slightly off topic but at the same time it is probably somehting that many of you have had much experience in 'real-world' scenarios) can I ask whether CGI::App users have any favourite ways to do it re 'web services' ie remote methods/apis that do something then return some data? SOAP, XML-RPC, bespoke XML/JSON/other in response to GET/POST with CGI params, any other approach? My methods and responses are very simple. For simplicity (speed, human readability, etc) you can't beat JSON. I love it. And if you allow some JSONP you can make it easy for people to use your service to build mashups. You can have your clients make submissions that are simple requests with a JSON document as part of the request or you can use normal CGI style parameters. Really up to you. I'd avoid SOAP if I were you. It's overly complex and there are a lots of different variations. Compatibility between systems is not given and can be a real big headache. It would be nice to have hassle free security already there - this was the one advantage to SOAP - the main disadvantage being a lack of understanding on my part... I could be completely wrong, but I don't see how SOAP provide security to your application? You still need to implement whatever security scheme you decide on and you can always use SOAP's basic security model for your own application if you want. But as far as security in web services goes I've had good success with the following: 1) username and passwords. Treat it just like other web stuff. The only difference is that you don't really use a cookie, you just make them send the username and password on every request. 2) crytographic token. Very similar to #1 but instead of passing a username and pw with each request it's just a simple token. You'd give each client a separate token which you can then verify on each request. You can also embed data into the token itself like client id, etc. You can even embed something like the origin IP address in there so that client can't give your tokens away to other people. -- Michael Peters Plus Three, LP # CGI::Application community mailing list #### ## To unsubscribe, or change your message delivery options, ## ## visit: http://www.erlbaum.net/mailman/listinfo/cgiapp## #### ## Web archive: http://www.erlbaum.net/pipermail/cgiapp/ ## ## Wiki: http://cgiapp.erlbaum.net/ ## ####
[cgiapp] Re: New plugin idea based/inspired on CA Dispatch.
I already started writing a CA plugin and I'd love to hear what you all think (if the idea/plugin can be useful or just a waste of time). I have my own thoughts but I can be missing something and I'd like to have other opinions. Based and inspired in CA Dispatch, also borrowing some code, the plugin should work as a *light* implementation from CA Dispatch for simple CA based apps. In my daily work, I usually write simple CA apps, always with a couple of runmodes (usually, around 8) and a single application module (no need to have more, since the apps usually are fairly simple). Also, I usually need to implement clean url's. In this context, what I did so far is to adapt the url parsing routine from CA Dispatch (receiving from the CA app a dispatch table in the same way CA Dispatch does) and *adding* the parsed params/values into CGI.pm params, in a way they can be retrieved in the CA based app with the usual $app-query-param('parsed_param_name'); method. Since this is my first plugin AND I never been in touch with CA other than doing my simple CA apps, I dont know if this idea is good, ok, heresy or just stupid. Porta, I think is a great idea. I really like it. I could also see it being used along with ::Dispatch: -- The global dispatcher might handle passing the flow into the right module, and then this plugin would pick up from there. While a global dispatcher is nice, sometimes it's more helpful to keep the the related dispatch table and run modes closer together. In my workflow, I found a global Dispatch.pm to be a point of conflict, in the source control sense: Two unrelated projects may both modify a global Dispatch.pm. When I go to launch one project, the other project becomes a dependency. (I solved that by recording changes to Dispatch.pm separately from other work). I have some specific suggestions on your implementation: - rename routes_table to just routes. I don't think the word table adds much. - Consider having routes_table() automatically add every run mode dispatched to the run_modes hash, if a subroutine with that name exists in the current scope. (I suppose you can use the can() method to test for that? ). That will eliminate the need to make a separate call to run_modes() in most cases, unless you have a run mode that points to a code-ref that you need to call. Mark -- . . . . . . . . . . . . . . . . . . . . . . . . . . . Mark StosbergPrincipal Developer [EMAIL PROTECTED] Summersault, LLC 765-939-9301 ext 202 database driven websites . . . . . http://www.summersault.com/ . . . . . . . . # CGI::Application community mailing list #### ## To unsubscribe, or change your message delivery options, ## ## visit: http://www.erlbaum.net/mailman/listinfo/cgiapp## #### ## Web archive: http://www.erlbaum.net/pipermail/cgiapp/ ## ## Wiki: http://cgiapp.erlbaum.net/ ## ####
[cgiapp] Re: New plugin idea based/inspired on CA Dispatch.
On Mon, 22 Sep 2008 11:36:24 -0400 Mark Stosberg [EMAIL PROTECTED] wrote: I already started writing a CA plugin and I'd love to hear what you all think (if the idea/plugin can be useful or just a waste of time). I have my own thoughts but I can be missing something and I'd like to have other opinions. Based and inspired in CA Dispatch, also borrowing some code, the plugin should work as a *light* implementation from CA Dispatch for simple CA based apps. In my daily work, I usually write simple CA apps, always with a couple of runmodes (usually, around 8) and a single application module (no need to have more, since the apps usually are fairly simple). Also, I usually need to implement clean url's. In this context, what I did so far is to adapt the url parsing routine from CA Dispatch (receiving from the CA app a dispatch table in the same way CA Dispatch does) and *adding* the parsed params/values into CGI.pm params, in a way they can be retrieved in the CA based app with the usual $app-query-param('parsed_param_name'); method. Since this is my first plugin AND I never been in touch with CA other than doing my simple CA apps, I dont know if this idea is good, ok, heresy or just stupid. Porta, I think is a great idea. I really like it. I could also see it being used along with ::Dispatch: -- The global dispatcher might handle passing the flow into the right module, and then this plugin would pick up from there. While a global dispatcher is nice, sometimes it's more helpful to keep the the related dispatch table and run modes closer together. In my workflow, I found a global Dispatch.pm to be a point of conflict, in the source control sense: Two unrelated projects may both modify a global Dispatch.pm. When I go to launch one project, the other project becomes a dependency. (I solved that by recording changes to Dispatch.pm separately from other work). I have some specific suggestions on your implementation: - rename routes_table to just routes. I don't think the word table adds much. - Consider having routes_table() automatically add every run mode dispatched to the run_modes hash, if a subroutine with that name exists in the current scope. (I suppose you can use the can() method to test for that? ). That will eliminate the need to make a separate call to run_modes() in most cases, unless you have a run mode that points to a code-ref that you need to call. One more suggestion: Break out all the code in the 'for' loop that processes a single route into it's own subroutine. That would allow someone to 'use' this plugin and build on it to parse the 'route' out of a subroutine attribute, like Catalyst does. And perhaps one more suggestion: Perhaps there should be an option to set a path for which all the routes are relative to. For example: $c-routes_root('/app/volunteer/profile'); And then in the routing table, or in a potential signature, you can be relative to that: $c-route( # maps to /app/volunteer/profile/edit/:id 'edit/:id' = 'edit' ); # Or sub edit ('/edit/:id') { } Now, when I saw Matt Trout, a Catalyst maintainer at YAPC, he was having second thoughts about using subroutine attributes in Catalyst, although he didn't go into detail. And I have run into problems with them in the past. So, I'm not recommending that style as being preferred, but I think it's an option some people might enjoy having. Mark # CGI::Application community mailing list #### ## To unsubscribe, or change your message delivery options, ## ## visit: http://www.erlbaum.net/mailman/listinfo/cgiapp## #### ## Web archive: http://www.erlbaum.net/pipermail/cgiapp/ ## ## Wiki: http://cgiapp.erlbaum.net/ ## ####
Re: [cgiapp] Best practice for CGI errors
Mark Knoop wrote: ...while I am here (and acknowledging that this is slightly off topic but at the same time it is probably somehting that many of you have had much experience in 'real-world' scenarios) can I ask whether CGI::App users have any favourite ways to do it re 'web services' ie remote methods/apis that do something then return some data? SOAP, XML-RPC, bespoke XML/JSON/other in response to GET/POST with CGI params, any other approach? My methods and responses are very simple. For simplicity (speed, human readability, etc) you can't beat JSON. I love it. And if you allow some JSONP you can make it easy for people to use your service to build mashups. You can have your clients make submissions that are simple requests with a JSON document as part of the request or you can use normal CGI style parameters. Really up to you. I'd avoid SOAP if I were you. It's overly complex and there are a lots of different variations. Compatibility between systems is not given and can be a real big headache. It would be nice to have hassle free security already there - this was the one advantage to SOAP - the main disadvantage being a lack of understanding on my part... I could be completely wrong, but I don't see how SOAP provide security to your application? You still need to implement whatever security scheme you decide on and you can always use SOAP's basic security model for your own application if you want. But as far as security in web services goes I've had good success with the following: 1) username and passwords. Treat it just like other web stuff. The only difference is that you don't really use a cookie, you just make them send the username and password on every request. 2) crytographic token. Very similar to #1 but instead of passing a username and pw with each request it's just a simple token. You'd give each client a separate token which you can then verify on each request. You can also embed data into the token itself like client id, etc. You can even embed something like the origin IP address in there so that client can't give your tokens away to other people. -- Michael Peters Plus Three, LP Thanks for this. I like the look of JSON(P)... will investigate further as an alternative to XML. Re SOAP security it was just that I had working examples of clients accessing a proxy via ssl but I guess that there is no reason why I cannot use https with a normal CGI request - I just never have done (or at least not with a dynamic client as opposed to a browser). Username and password just get passed as normal parameters so as long as they are ssl'd that's fine. Best, Mark # CGI::Application community mailing list #### ## To unsubscribe, or change your message delivery options, ## ## visit: http://www.erlbaum.net/mailman/listinfo/cgiapp## #### ## Web archive: http://www.erlbaum.net/pipermail/cgiapp/ ## ## Wiki: http://cgiapp.erlbaum.net/ ## ####
[cgiapp] Re: New plugin idea based/inspired on CA Dispatch.
Now, when I saw Matt Trout, a Catalyst maintainer at YAPC, he was having second thoughts about using subroutine attributes in Catalyst, although he didn't go into detail. And I have run into problems with them in the past. So, I'm not recommending that style as being preferred, but I think it's an option some people might enjoy having. Here's a current conversation about the past and future of subroutine attributes in Catalyst: http://use.perl.org/comments.pl?sid=41074cid=65070 It does sound questionable that using them as a core framework feature giving the state of what's possible (and works well) with Perl now. Mark # CGI::Application community mailing list #### ## To unsubscribe, or change your message delivery options, ## ## visit: http://www.erlbaum.net/mailman/listinfo/cgiapp## #### ## Web archive: http://www.erlbaum.net/pipermail/cgiapp/ ## ## Wiki: http://cgiapp.erlbaum.net/ ## ####
Re: [cgiapp] Best practice for CGI errors
On Mon, 22 Sep 2008, Mark Knoop wrote: If one wants to return an error to the client because they have not included the correct parameters for the CGI request, should one use one of the HTTP status codes and if so which one? And then is it ok/sensible to include an error message in the body? If you've drunk the REST koolaid (or like me drained the entire pitcher :-) ) you should always be thinking of leveraging HTTP features as much as possible and that would mean using status codes. I would suggest 400 ('Bad request') An error message in the body is good for providing additional info to humans but the API of your web service should not depend on it in any way. -- Jaldhar H. Vyas [EMAIL PROTECTED] # CGI::Application community mailing list #### ## To unsubscribe, or change your message delivery options, ## ## visit: http://www.erlbaum.net/mailman/listinfo/cgiapp## #### ## Web archive: http://www.erlbaum.net/pipermail/cgiapp/ ## ## Wiki: http://cgiapp.erlbaum.net/ ## ####
[cgiapp] Re: New plugin idea based/inspired on CA Dispatch.
Mark. Thanks for your feedback. I already did the change you suggested to change routes_table to routes. But I must to admit that is not clear to me what you mean with this one. - Consider having routes_table() automatically add every run mode dispatched to the run_modes hash, if a subroutine with that name exists in the current scope. (I suppose you can use the can() method to test for that? ). Maybe because I'm not pro-efficient with perl enough, or maybe I'm missing something? Also,. I liked this: Perhaps there should be an option to set a path for which all the routes are relative to. For example: $c-routes_root('/app/volunteer/profile'); I definitely going to include that change. But, about the catalyst style, I didn't liked the approach, and, also, see something (I think almost) exactly like that in CAP::Actiondispatch (http://search.cpan.org/~jaywhy/CGI-Application-Plugin-ActionDispatch-0.96/lib/CGI/Application/Plugin/ActionDispatch.pm) and I really didn't liked it (or just didn't worked for me). Thanks. Julián Porta. # CGI::Application community mailing list #### ## To unsubscribe, or change your message delivery options, ## ## visit: http://www.erlbaum.net/mailman/listinfo/cgiapp## #### ## Web archive: http://www.erlbaum.net/pipermail/cgiapp/ ## ## Wiki: http://cgiapp.erlbaum.net/ ## ####
[cgiapp] Patches available for ::Plugin::Routes (was: Re: New plugin idea based/inspired on CA Dispatch)
I already did the change you suggested to change routes_table to routes. Great. with this one. - Consider having routes_table() automatically add every run mode dispatched to the run_modes hash, if a subroutine with that name exists in the current scope. (I suppose you can use the can() method to test for that? ). Maybe because I'm not pro-efficient with perl enough, or maybe I'm missing something? I've sent you patches via github that implement this for you now. You can browse them here: http://github.com/markstos/cgi--application--plugin--routes/commits/master When registering routes, we also try to automatically register the run mode names. We will register a run mode when there is not already one defined with the target name and we 'can' call a method with the same name. This means that for you common cases when you call 'routes', you can skip calling run_modes(). My other patches improved your 'import' routine, created proper automated tests, and made sure Data::Dumper was only loaded if it was required. Also,. I liked this: Perhaps there should be an option to set a path for which all the routes are relative to. For example: $c-routes_root('/app/volunteer/profile'); I definitely going to include that change. Great! But, about the catalyst style, I didn't liked the approach, and, also, see something (I think almost) exactly like that in CAP::Actiondispatch (http://search.cpan.org/~jaywhy/CGI-Application-Plugin-ActionDispatch-0.96/lib/CGI/Application/Plugin/ActionDispatch.pm) and I really didn't liked it (or just didn't worked for me). I had forgetten about that. I never used it myself. I think I prefer the approach in this new plugin. A bit of further feedback: - Your POD coverage test is still failing. Mark -- http://mark.stosberg.com/ # CGI::Application community mailing list #### ## To unsubscribe, or change your message delivery options, ## ## visit: http://www.erlbaum.net/mailman/listinfo/cgiapp## #### ## Web archive: http://www.erlbaum.net/pipermail/cgiapp/ ## ## Wiki: http://cgiapp.erlbaum.net/ ## ####
[cgiapp] RE: Patches available for ::Plugin::Routes (was: Re: New plugin idea based/inspired on CA Dispatch)
Wonderful changes. I'll review the POD problem. First time with it. Thanks. Julián. I already did the change you suggested to change routes_table to routes. Great. with this one. - Consider having routes_table() automatically add every run mode dispatched to the run_modes hash, if a subroutine with that name exists in the current scope. (I suppose you can use the can() method to test for that? ). Maybe because I'm not pro-efficient with perl enough, or maybe I'm missing something? I've sent you patches via github that implement this for you now. You can browse them here: http://github.com/markstos/cgi--application--plugin--routes/commits/master When registering routes, we also try to automatically register the run mode names. We will register a run mode when there is not already one defined with the target name and we 'can' call a method with the same name. This means that for you common cases when you call 'routes', you can skip calling run_modes(). My other patches improved your 'import' routine, created proper automated tests, and made sure Data::Dumper was only loaded if it was required. Also,. I liked this: Perhaps there should be an option to set a path for which all the routes are relative to. For example: $c-routes_root('/app/volunteer/profile'); I definitely going to include that change. Great! But, about the catalyst style, I didn't liked the approach, and, also, see something (I think almost) exactly like that in CAP::Actiondispatch (http://search.cpan.org/~jaywhy/CGI-Application-Plugin-ActionDispatch-0.96/lib/CGI/Application/Plugin/ActionDispatch.pm) and I really didn't liked it (or just didn't worked for me). I had forgetten about that. I never used it myself. I think I prefer the approach in this new plugin. A bit of further feedback: - Your POD coverage test is still failing. Mark -- http://mark.stosberg.com/ # CGI::Application community mailing list #### ## To unsubscribe, or change your message delivery options, ## ## visit: http://www.erlbaum.net/mailman/listinfo/cgiapp## #### ## Web archive: http://www.erlbaum.net/pipermail/cgiapp/ ## ## Wiki: http://cgiapp.erlbaum.net/ ## ####