You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@couchdb.apache.org by jc...@apache.org on 2009/04/17 02:47:50 UTC

svn commit: r765819 - in /couchdb/trunk: share/server/main.js src/couchdb/couch_httpd.erl src/couchdb/couch_httpd_view.erl

Author: jchris
Date: Fri Apr 17 00:47:50 2009
New Revision: 765819

URL: http://svn.apache.org/viewvc?rev=765819&view=rev
Log:
output errors differently during chunked responses (view and list)

Modified:
    couchdb/trunk/share/server/main.js
    couchdb/trunk/src/couchdb/couch_httpd.erl
    couchdb/trunk/src/couchdb/couch_httpd_view.erl

Modified: couchdb/trunk/share/server/main.js
URL: http://svn.apache.org/viewvc/couchdb/trunk/share/server/main.js?rev=765819&r1=765818&r2=765819&view=diff
==============================================================================
--- couchdb/trunk/share/server/main.js [utf-8] (original)
+++ couchdb/trunk/share/server/main.js [utf-8] Fri Apr 17 00:47:50 2009
@@ -414,7 +414,7 @@
   } catch(e) {
     log("function raised error: "+e.toString());
     log("stacktrace: "+e.stack);
-    var errorMessage = "function raised error: "+e.toString()+"\nstacktrace: "+e.stack;
+    var errorMessage = "JavaScript function raised error: "+e.toString()+"\nSee CouchDB logfile for stacktrace.";
     respond({error:"render_error",reason:errorMessage});
   }
 };

Modified: couchdb/trunk/src/couchdb/couch_httpd.erl
URL: http://svn.apache.org/viewvc/couchdb/trunk/src/couchdb/couch_httpd.erl?rev=765819&r1=765818&r2=765819&view=diff
==============================================================================
--- couchdb/trunk/src/couchdb/couch_httpd.erl (original)
+++ couchdb/trunk/src/couchdb/couch_httpd.erl Fri Apr 17 00:47:50 2009
@@ -21,7 +21,7 @@
 -export([primary_header_value/2,partition/1,serve_file/3]).
 -export([start_chunked_response/3,send_chunk/2]).
 -export([start_json_response/2, start_json_response/3, end_json_response/1]).
--export([send_response/4,send_method_not_allowed/2,send_error/4, send_redirect/2]).
+-export([send_response/4,send_method_not_allowed/2,send_error/4, send_redirect/2,send_chunked_error/2]).
 -export([send_json/2,send_json/3,send_json/4]).
 -export([default_authentication_handler/1,special_test_authentication_handler/1]).
 -export([null_authentication_handler/1]).
@@ -422,6 +422,9 @@
 error_info(Error) ->
     {500, <<"unknown_error">>, couch_util:to_binary(Error)}.
 
+send_error(_Req, {already_sent, _Error}) ->
+    ok;
+    
 send_error(Req, Error) ->
     {Code, ErrorStr, ReasonStr} = error_info(Error),
     if Code == 401 ->     
@@ -444,6 +447,23 @@
         {[{<<"error">>,  ErrorStr},
          {<<"reason">>, ReasonStr}]}).
 
+send_chunked_error(Resp, Error) ->
+    {Code, ErrorStr, ReasonStr} = error_info(Error),
+    CType = Resp:get_header_value("Content-Type"),
+    case CType of
+        "text/html" ->
+            HtmlError = ?l2b([$\n,
+                "<html><body><h2>Error: ", ErrorStr, "</h2>",
+                "<pre>Reason: ", ReasonStr, "</pre>", $\n]),
+            send_chunk(Resp, HtmlError);
+        _Else ->
+            JsonError = {[{<<"code">>, Code},
+                {<<"error">>,  ErrorStr}, 
+                {<<"reason">>, ReasonStr}]},
+            send_chunk(Resp, ?l2b([$\n,?JSON_ENCODE(JsonError),$\n]))
+    end,
+    send_chunk(Resp, []).
+
 send_redirect(Req, Path) ->
      Headers = [{"Location", couch_httpd:absolute_uri(Req, Path)}],
      send_response(Req, 301, Headers, <<>>).

Modified: couchdb/trunk/src/couchdb/couch_httpd_view.erl
URL: http://svn.apache.org/viewvc/couchdb/trunk/src/couchdb/couch_httpd_view.erl?rev=765819&r1=765818&r2=765819&view=diff
==============================================================================
--- couchdb/trunk/src/couchdb/couch_httpd_view.erl (original)
+++ couchdb/trunk/src/couchdb/couch_httpd_view.erl Fri Apr 17 00:47:50 2009
@@ -20,7 +20,8 @@
 
 -import(couch_httpd,
     [send_json/2,send_json/3,send_json/4,send_method_not_allowed/2,send_chunk/2,
-    start_json_response/2, start_json_response/3, end_json_response/1]).
+    start_json_response/2, start_json_response/3, end_json_response/1,
+    send_chunked_error/2]).
 
 design_doc_view(Req, Db, Id, ViewName, Keys) ->
     #view_query_args{
@@ -500,7 +501,7 @@
     Helpers#view_fold_helper_funs{
         passed_end = PassedEnd2,
         start_response = StartResp2,
-        send_row = SendRow2
+        send_row = wrap_for_chunked_errors(SendRow2)
     }.
 
 apply_default_helper_funs(#reduce_fold_helper_funs{
@@ -519,7 +520,7 @@
 
     Helpers#reduce_fold_helper_funs{
         start_response = StartResp2,
-        send_row = SendRow2
+        send_row = wrap_for_chunked_errors(SendRow2)
     }.
 
 make_passed_end_fun(fwd, EndKey, EndDocId, InclusiveEnd) ->
@@ -578,6 +579,26 @@
     end,
     send_chunk(Resp, RowFront2 ++ ?JSON_ENCODE({[{key, Key}, {value, Value}]})).
 
+wrap_for_chunked_errors(Fun) when is_function(Fun, 3)->
+    fun(Resp, B, C) ->
+        try Fun(Resp, B, C)
+        catch
+            throw:Error ->
+                send_chunked_error(Resp, Error),
+                throw({already_sent, Error})
+        end
+    end;
+
+wrap_for_chunked_errors(Fun) when is_function(Fun, 5)->
+    fun(Resp, B, C, D, E) ->
+        try Fun(Resp, B, C, D, E)
+        catch
+            throw:Error ->
+                send_chunked_error(Resp, Error),
+                throw({already_sent, Error})
+        end
+    end.    
+
 view_group_etag(Group) ->
     view_group_etag(Group, nil).