You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@couchdb.apache.org by rn...@apache.org on 2014/08/28 13:59:59 UTC

[36/50] chttpd commit: updated refs/heads/master to 58020ab

Add CORS support


Project: http://git-wip-us.apache.org/repos/asf/couchdb-chttpd/repo
Commit: http://git-wip-us.apache.org/repos/asf/couchdb-chttpd/commit/6deefa1c
Tree: http://git-wip-us.apache.org/repos/asf/couchdb-chttpd/tree/6deefa1c
Diff: http://git-wip-us.apache.org/repos/asf/couchdb-chttpd/diff/6deefa1c

Branch: refs/heads/master
Commit: 6deefa1c34bb855ef9304ca2ea4f1f45a7df2193
Parents: 57d1078
Author: Robert Newson <rn...@apache.org>
Authored: Wed Jul 30 11:05:41 2014 +0100
Committer: Robert Newson <rn...@apache.org>
Committed: Thu Jul 31 11:55:10 2014 +0100

----------------------------------------------------------------------
 src/chttpd.erl      | 53 ++++++++++++++++++++++++++++++++----------------
 src/chttpd_cors.erl | 21 +++++++++++++++++++
 2 files changed, 56 insertions(+), 18 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/couchdb-chttpd/blob/6deefa1c/src/chttpd.erl
----------------------------------------------------------------------
diff --git a/src/chttpd.erl b/src/chttpd.erl
index d671812..c41707f 100644
--- a/src/chttpd.erl
+++ b/src/chttpd.erl
@@ -200,10 +200,15 @@ handle_request(MochiReq) ->
     Result =
     try
         check_request_uri_length(RawUri),
-        case authenticate_request(HttpReq, AuthenticationFuns) of
-        #httpd{} = Req ->
-            HandlerFun = url_handler(HandlerKey),
-            HandlerFun(chttpd_auth_request:authorize_request(possibly_hack(Req)));
+        case chttpd_cors:is_preflight_request(HttpReq) of
+        #httpd{} ->
+            case authenticate_request(HttpReq, AuthenticationFuns) of
+            #httpd{} = Req ->
+                HandlerFun = url_handler(HandlerKey),
+                HandlerFun(chttpd_auth_request:authorize_request(possibly_hack(Req)));
+            Response ->
+                Response
+            end;
         Response ->
             Response
         end
@@ -407,8 +412,10 @@ primary_header_value(#httpd{mochi_req=MochiReq}, Key) ->
     MochiReq:get_primary_header_value(Key).
 
 serve_file(#httpd{mochi_req=MochiReq}=Req, RelativePath, DocumentRoot) ->
+    Headers = server_header() ++
+	couch_httpd_auth:cookie_auth_header(Req, []),
     {ok, MochiReq:serve_file(RelativePath, DocumentRoot,
-        server_header() ++ couch_httpd_auth:cookie_auth_header(Req, []))}.
+        chttpd_cors:headers(Req, Headers))}.
 
 qs_value(Req, Key) ->
     qs_value(Req, Key, undefined).
@@ -536,7 +543,8 @@ etag_respond(Req, CurrentEtag, RespFun) ->
     case etag_match(Req, CurrentEtag) of
     true ->
         % the client has this in their cache.
-        chttpd:send_response(Req, 304, [{"Etag", CurrentEtag}], <<>>);
+        Headers = chttpd_cors:headers(Req, [{"Etag", CurrentEtag}]),
+        chttpd:send_response(Req, 304, Headers, <<>>);
     false ->
         % Run the function.
         RespFun()
@@ -548,10 +556,12 @@ verify_is_server_admin(#httpd{user_ctx=#user_ctx{roles=Roles}}) ->
     false -> throw({unauthorized, <<"You are not a server admin.">>})
     end.
 
-start_response_length(#httpd{mochi_req=MochiReq}=Req, Code, Headers, Length) ->
+start_response_length(#httpd{mochi_req=MochiReq}=Req, Code, Headers0, Length) ->
     couch_stats_collector:increment({httpd_status_codes, Code}),
-    Resp = MochiReq:start_response_length({Code, Headers ++ server_header() ++
-        couch_httpd_auth:cookie_auth_header(Req, Headers), Length}),
+    Headers = Headers0 ++ server_header() ++
+	couch_httpd_auth:cookie_auth_header(Req, Headers0),
+    Resp = MochiReq:start_response_length({Code,
+        chttpd_cors:headers(Req, Headers), Length}),
     case MochiReq:get(method) of
     'HEAD' -> throw({http_head_abort, Resp});
     _ -> ok
@@ -562,10 +572,12 @@ send(Resp, Data) ->
     Resp:send(Data),
     {ok, Resp}.
 
-start_chunked_response(#httpd{mochi_req=MochiReq}=Req, Code, Headers) ->
+start_chunked_response(#httpd{mochi_req=MochiReq}=Req, Code, Headers0) ->
     couch_stats_collector:increment({httpd_status_codes, Code}),
-    Resp = MochiReq:respond({Code, Headers ++ server_header() ++
-        couch_httpd_auth:cookie_auth_header(Req, Headers), chunked}),
+    Headers = Headers0 ++ server_header() ++
+        couch_httpd_auth:cookie_auth_header(Req, Headers0),
+    Resp = MochiReq:respond({Code, chttpd_cors:headers(Req, Headers),
+        chunked}),
     case MochiReq:get(method) of
     'HEAD' -> throw({http_head_abort, Resp});
     _ -> ok
@@ -576,10 +588,12 @@ send_chunk(Resp, Data) ->
     Resp:write_chunk(Data),
     {ok, Resp}.
 
-send_response(#httpd{mochi_req=MochiReq}=Req, Code, Headers, Body) ->
+send_response(#httpd{mochi_req=MochiReq}=Req, Code, Headers0, Body) ->
     couch_stats_collector:increment({httpd_status_codes, Code}),
-    {ok, MochiReq:respond({Code, Headers ++ server_header() ++
-        couch_httpd_auth:cookie_auth_header(Req, Headers), Body})}.
+    Headers = Headers0 ++ server_header() ++
+	couch_httpd_auth:cookie_auth_header(Req, Headers0),
+    {ok, MochiReq:respond({Code, Headers, Body})}.
+
 
 send_method_not_allowed(Req, Methods) ->
     send_error(Req, 405, [{"Allow", Methods}], <<"method_not_allowed">>,
@@ -591,13 +605,15 @@ send_json(Req, Value) ->
 send_json(Req, Code, Value) ->
     send_json(Req, Code, [], Value).
 
-send_json(Req, Code, Headers, Value) ->
+send_json(Req, Code, Headers0, Value) ->
+    Headers = chttpd_cors:headers(Req, Headers0),
     couch_httpd:send_json(Req, Code, [timing(), reqid() | Headers], Value).
 
 start_json_response(Req, Code) ->
     start_json_response(Req, Code, []).
 
-start_json_response(Req, Code, Headers) ->
+start_json_response(Req, Code, Headers0) ->
+    Headers = chttpd_cors:headers(Req, Headers0),
     couch_httpd:start_json_response(Req, Code, [timing(), reqid() | Headers]).
 
 end_json_response(Resp) ->
@@ -840,7 +856,8 @@ send_chunked_error(Resp, Error) ->
     send_chunk(Resp, []).
 
 send_redirect(Req, Path) ->
-     Headers = [{"Location", chttpd:absolute_uri(Req, Path)}],
+     Headers = chttpd_cors:headers(Req,
+         [{"Location", chttpd:absolute_uri(Req, Path)}]),
      send_response(Req, 301, Headers, <<>>).
 
 server_header() ->

http://git-wip-us.apache.org/repos/asf/couchdb-chttpd/blob/6deefa1c/src/chttpd_cors.erl
----------------------------------------------------------------------
diff --git a/src/chttpd_cors.erl b/src/chttpd_cors.erl
new file mode 100644
index 0000000..03ec289
--- /dev/null
+++ b/src/chttpd_cors.erl
@@ -0,0 +1,21 @@
+% Licensed under the Apache License, Version 2.0 (the "License"); you may not
+% use this file except in compliance with the License. You may obtain a copy of
+% the License at
+%
+%   http://www.apache.org/licenses/LICENSE-2.0
+%
+% Unless required by applicable law or agreed to in writing, software
+% distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+% WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+% License for the specific language governing permissions and limitations under
+% the License.
+
+-module(chttpd_cors).
+
+-export([is_preflight_request/1, headers/2]).
+
+is_preflight_request(Req) ->
+    couch_httpd_cors:is_preflight_request(Req).
+
+headers(Req, Headers) ->
+    couch_httpd_cors:cors_headers(Req, Headers).