aboutsummaryrefslogtreecommitdiffstats
path: root/lib/dialyzer/test/r9c_tests_SUITE_data/src/inets/httpc_handler.erl
diff options
context:
space:
mode:
Diffstat (limited to 'lib/dialyzer/test/r9c_tests_SUITE_data/src/inets/httpc_handler.erl')
-rw-r--r--lib/dialyzer/test/r9c_tests_SUITE_data/src/inets/httpc_handler.erl724
1 files changed, 0 insertions, 724 deletions
diff --git a/lib/dialyzer/test/r9c_tests_SUITE_data/src/inets/httpc_handler.erl b/lib/dialyzer/test/r9c_tests_SUITE_data/src/inets/httpc_handler.erl
deleted file mode 100644
index 5076a12aaa..0000000000
--- a/lib/dialyzer/test/r9c_tests_SUITE_data/src/inets/httpc_handler.erl
+++ /dev/null
@@ -1,724 +0,0 @@
-%% ``The contents of this file are subject to the Erlang Public License,
-%% Version 1.1, (the "License"); you may not use this file except in
-%% compliance with the License. You should have received a copy of the
-%% Erlang Public License along with this software. If not, it can be
-%% retrieved via the world wide web at http://www.erlang.org/.
-%%
-%% Software distributed under the License is distributed on an "AS IS"
-%% basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
-%% the License for the specific language governing rights and limitations
-%% under the License.
-%%
-%% The Initial Developer of the Original Code is Mobile Arts AB
-%% Portions created by Mobile Arts are Copyright 2002, Mobile Arts AB
-%% All Rights Reserved.''
-%%
-%%
-
-%%% TODO:
-%%% - If an error is returned when sending a request, don't use this
-%%% session anymore.
-%%% - Closing of sessions not properly implemented for some cases
-
-%%% File : httpc_handler.erl
-%%% Author : Johan Blom <[email protected]>
-%%% Description : Handles HTTP client responses, for a single TCP session
-%%% Created : 4 Mar 2002 by Johan Blom
-
--module(httpc_handler).
-
--include("http.hrl").
--include("jnets_httpd.hrl").
-
--export([init_connection/2,http_request/2]).
-
-%%% ==========================================================================
-%%% "Main" function in the spawned process for the session.
-init_connection(Req,Session) when record(Req,request) ->
- case catch http_lib:connect(Req) of
- {ok,Socket} ->
- case catch http_request(Req,Socket) of
- ok ->
- case Session#session.clientclose of
- true ->
- ok;
- false ->
- httpc_manager:register_socket(Req#request.address,
- Session#session.id,
- Socket)
- end,
- next_response_with_request(Req,
- Session#session{socket=Socket});
- {error,Reason} -> % Not possible to use new session
- gen_server:cast(Req#request.from,
- {Req#request.ref,Req#request.id,{error,Reason}}),
- exit_session_ok(Req#request.address,
- Session#session{socket=Socket})
- end;
- {error,Reason} -> % Not possible to set up new session
- gen_server:cast(Req#request.from,
- {Req#request.ref,Req#request.id,{error,Reason}}),
- exit_session_ok2(Req#request.address,
- Session#session.clientclose,Session#session.id)
- end.
-
-next_response_with_request(Req,Session) ->
- Timeout=(Req#request.settings)#client_settings.timeout,
- case catch read(Timeout,Session#session.scheme,Session#session.socket) of
- {Status,Headers,Body} ->
- NewReq=handle_response({Status,Headers,Body},Timeout,Req,Session),
- next_response_with_request(NewReq,Session);
- {error,Reason} ->
- gen_server:cast(Req#request.from,
- {Req#request.ref,Req#request.id,{error,Reason}}),
- exit_session(Req#request.address,Session,aborted_request);
- {'EXIT',Reason} ->
- gen_server:cast(Req#request.from,
- {Req#request.ref,Req#request.id,{error,Reason}}),
- exit_session(Req#request.address,Session,aborted_request)
- end.
-
-handle_response(Response,Timeout,Req,Session) ->
- case http_response(Response,Req,Session) of
- ok ->
- next_response(Timeout,Req#request.address,Session);
- stop ->
- exit(normal);
- {error,Reason} ->
- gen_server:cast(Req#request.from,
- {Req#request.ref,Req#request.id,{error,Reason}}),
- exit_session(Req#request.address,Session,aborted_request)
- end.
-
-
-
-%%% Wait for the next respond until
-%%% - session is closed by the other side
-%%% => set up a new a session, if there are pending requests in the que
-%%% - "Connection:close" header is received
-%%% => close the connection (release socket) then
-%%% set up a new a session, if there are pending requests in the que
-%%%
-%%% Note:
-%%% - When invoked there are no pending responses on received requests.
-%%% - Never close the session explicitly, let it timeout instead!
-next_response(Timeout,Address,Session) ->
- case httpc_manager:next_request(Address,Session#session.id) of
- no_more_requests ->
- %% There are no more pending responses, now just wait for
- %% timeout or a new response.
- case catch read(Timeout,
- Session#session.scheme,Session#session.socket) of
- {error,Reason} when Reason==session_remotely_closed;
- Reason==session_local_timeout ->
- exit_session_ok(Address,Session);
- {error,Reason} ->
- exit_session(Address,Session,aborted_request);
- {'EXIT',Reason} ->
- exit_session(Address,Session,aborted_request);
- {Status2,Headers2,Body2} ->
- case httpc_manager:next_request(Address,
- Session#session.id) of
- no_more_requests -> % Should not happen!
- exit_session(Address,Session,aborted_request);
- {error,Reason} -> % Should not happen!
- exit_session(Address,Session,aborted_request);
- NewReq ->
- handle_response({Status2,Headers2,Body2},
- Timeout,NewReq,Session)
- end
- end;
- {error,Reason} -> % The connection has been closed by httpc_manager
- exit_session(Address,Session,aborted_request);
- NewReq ->
- NewReq
- end.
-
-%% ===========================================================================
-%% Internals
-
-%%% Read in and parse response data from the socket
-read(Timeout,SockType,Socket) ->
- Info=#response{scheme=SockType,socket=Socket},
- http_lib:setopts(SockType,Socket,[{packet, http}]),
- Info1=read_response(SockType,Socket,Info,Timeout),
- http_lib:setopts(SockType,Socket,[binary,{packet, raw}]),
- case (Info1#response.headers)#res_headers.content_type of
- "multipart/byteranges"++Param ->
- range_response_body(Info1,Timeout,Param);
- _ ->
- #response{status=Status2,headers=Headers2,body=Body2}=
- http_lib:read_client_body(Info1,Timeout),
- {Status2,Headers2,Body2}
- end.
-
-
-%%% From RFC 2616:
-%%% Status-Line = HTTP-Version SP Status-Code SP Reason-Phrase CRLF
-%%% HTTP-Version = "HTTP" "/" 1*DIGIT "." 1*DIGIT
-%%% Status-Code = 3DIGIT
-%%% Reason-Phrase = *<TEXT, excluding CR, LF>
-read_response(SockType,Socket,Info,Timeout) ->
- case http_lib:recv0(SockType,Socket,Timeout) of
- {ok,{http_response,{1,VerMin}, Status, _Phrase}} when VerMin==0;
- VerMin==1 ->
- Info1=Info#response{status=Status,http_version=VerMin},
- http_lib:read_client_headers(Info1,Timeout);
- {ok,{http_response,_Version, _Status, _Phrase}} ->
- throw({error,bad_status_line});
- {error, timeout} ->
- throw({error,session_local_timeout});
- {error, Reason} when Reason==closed;Reason==enotconn ->
- throw({error,session_remotely_closed});
- {error, Reason} ->
- throw({error,Reason})
- end.
-
-%%% From RFC 2616, Section 4.4, Page 34
-%% 4.If the message uses the media type "multipart/byteranges", and the
-%% transfer-length is not otherwise specified, then this self-
-%% delimiting media type defines the transfer-length. This media type
-%% MUST NOT be used unless the sender knows that the recipient can parse
-%% it; the presence in a request of a Range header with multiple byte-
-%% range specifiers from a 1.1 client implies that the client can parse
-%% multipart/byteranges responses.
-%%% FIXME !!
-range_response_body(Info,Timeout,Param) ->
- Headers=Info#response.headers,
- case {Headers#res_headers.content_length,
- Headers#res_headers.transfer_encoding} of
- {undefined,undefined} ->
- #response{status=Status2,headers=Headers2,body=Body2}=
- http_lib:read_client_multipartrange_body(Info,Param,Timeout),
- {Status2,Headers2,Body2};
- _ ->
- #response{status=Status2,headers=Headers2,body=Body2}=
- http_lib:read_client_body(Info,Timeout),
- {Status2,Headers2,Body2}
- end.
-
-
-%%% ----------------------------------------------------------------------------
-%%% Host: field is required when addressing multi-homed sites ...
-%%% It must not be present when the request is being made to a proxy.
-http_request(#request{method=Method,id=Id,
- scheme=Scheme,address={Host,Port},pathquery=PathQuery,
- headers=Headers, content={ContentType,Body},
- settings=Settings},
- Socket) ->
- PostData=
- if
- Method==post;Method==put ->
- case Headers#req_headers.expect of
- "100-continue" ->
- content_type_header(ContentType) ++
- content_length_header(length(Body)) ++
- "\r\n";
- _ ->
- content_type_header(ContentType) ++
- content_length_header(length(Body)) ++
- "\r\n" ++ Body
- end;
- true ->
- "\r\n"
- end,
- Message=
- case useProxy(Settings#client_settings.useproxy,
- {Scheme,Host,Port,PathQuery}) of
- false ->
- method(Method)++" "++PathQuery++" HTTP/1.1\r\n"++
- host_header(Host)++te_header()++
- headers(Headers) ++ PostData;
- AbsURI ->
- method(Method)++" "++AbsURI++" HTTP/1.1\r\n"++
- te_header()++
- headers(Headers)++PostData
- end,
- http_lib:send(Scheme,Socket,Message).
-
-useProxy(false,_) ->
- false;
-useProxy(true,{Scheme,Host,Port,PathQuery}) ->
- [atom_to_list(Scheme),"://",Host,":",integer_to_list(Port),PathQuery].
-
-
-
-headers(#req_headers{expect=Expect,
- other=Other}) ->
- H1=case Expect of
- undefined ->[];
- _ -> "Expect: "++Expect++"\r\n"
- end,
- H1++headers_other(Other).
-
-
-headers_other([]) ->
- [];
-headers_other([{Key,Value}|Rest]) when atom(Key) ->
- Head = atom_to_list(Key)++": "++Value++"\r\n",
- Head ++ headers_other(Rest);
-headers_other([{Key,Value}|Rest]) ->
- Head = Key++": "++Value++"\r\n",
- Head ++ headers_other(Rest).
-
-host_header(Host) ->
- "Host: "++lists:concat([Host])++"\r\n".
-content_type_header(ContentType) ->
- "Content-Type: " ++ ContentType ++ "\r\n".
-content_length_header(ContentLength) ->
- "Content-Length: "++integer_to_list(ContentLength) ++ "\r\n".
-te_header() ->
- "TE: \r\n".
-
-method(Method) ->
- httpd_util:to_upper(atom_to_list(Method)).
-
-
-%%% ----------------------------------------------------------------------------
-http_response({Status,Headers,Body},Req,Session) ->
- case Status of
- 100 ->
- status_continue(Req,Session);
- 200 ->
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {Status,Headers,Body}}),
- ServerClose=http_lib:connection_close(Headers),
- handle_connection(Session#session.clientclose,ServerClose,
- Req,Session);
- 300 -> status_multiple_choices(Headers,Body,Req,Session);
- 301 -> status_moved_permanently(Req#request.method,
- Headers,Body,Req,Session);
- 302 -> status_found(Headers,Body,Req,Session);
- 303 -> status_see_other(Headers,Body,Req,Session);
- 304 -> status_not_modified(Headers,Body,Req,Session);
- 305 -> status_use_proxy(Headers,Body,Req,Session);
- %% 306 This Status code is not used in HTTP 1.1
- 307 -> status_temporary_redirect(Headers,Body,Req,Session);
- 503 -> status_service_unavailable({Status,Headers,Body},Req,Session);
- Status50x when Status50x==500;Status50x==501;Status50x==502;
- Status50x==504;Status50x==505 ->
- status_server_error_50x({Status,Headers,Body},Req,Session);
- _ -> % FIXME May want to take some action on other Status codes as well
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {Status,Headers,Body}}),
- ServerClose=http_lib:connection_close(Headers),
- handle_connection(Session#session.clientclose,ServerClose,
- Req,Session)
- end.
-
-
-%%% Status code dependent functions.
-
-%%% Received a 100 Status code ("Continue")
-%%% From RFC2616
-%%% The client SHOULD continue with its request. This interim response is
-%%% used to inform the client that the initial part of the request has
-%%% been received and has not yet been rejected by the server. The client
-%%% SHOULD continue by sending the remainder of the request or, if the
-%%% request has already been completed, ignore this response. The server
-%%% MUST send a final response after the request has been completed. See
-%%% section 8.2.3 for detailed discussion of the use and handling of this
-%%% status code.
-status_continue(Req,Session) ->
- {_,Body}=Req#request.content,
- http_lib:send(Session#session.scheme,Session#session.socket,Body),
- next_response_with_request(Req,Session).
-
-
-%%% Received a 300 Status code ("Multiple Choices")
-%%% The resource is located in any one of a set of locations
-%%% - If a 'Location' header is present (preserved server choice), use that
-%%% to automatically redirect to the given URL
-%%% - else if the Content-Type/Body both are non-empty let the user agent make
-%%% the choice and thus return a response with status 300
-%%% Note:
-%%% - If response to a HEAD request, the Content-Type/Body both should be empty.
-%%% - The behaviour on an empty Content-Type or Body is unspecified.
-%%% However, e.g. "Apache/1.3" servers returns both empty if the header
-%%% 'if-modified-since: Date' was sent in the request and the content is
-%%% "not modified" (instead of 304). Thus implicitly giving the cache as the
-%%% only choice.
-status_multiple_choices(Headers,Body,Req,Session)
- when ((Req#request.settings)#client_settings.autoredirect)==true ->
- ServerClose=http_lib:connection_close(Headers),
- case Headers#res_headers.location of
- undefined ->
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {300,Headers,Body}}),
- handle_connection(Session#session.clientclose,ServerClose,
- Req,Session);
- RedirUrl ->
- Scheme=Session#session.scheme,
- case uri:parse(RedirUrl) of
- {error,Reason} ->
- {error,Reason};
- {Scheme,Host,Port,PathQuery} -> % Automatic redirection
- NewReq=Req#request{redircount=Req#request.redircount+1,
- address={Host,Port},pathquery=PathQuery},
- handle_redirect(Session#session.clientclose,ServerClose,
- NewReq,Session)
- end
- end;
-status_multiple_choices(Headers,Body,Req,Session) ->
- ServerClose=http_lib:connection_close(Headers),
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {300,Headers,Body}}),
- handle_connection(Session#session.clientclose,ServerClose,Req,Session).
-
-
-%%% Received a 301 Status code ("Moved Permanently")
-%%% The resource has been assigned a new permanent URI
-%%% - If a 'Location' header is present, use that to automatically redirect to
-%%% the given URL if GET or HEAD request
-%%% - else return
-%%% Note:
-%%% - The Body should contain a short hypertext note with a hyperlink to the
-%%% new URI. Return this if Content-Type acceptable (some HTTP servers doesn't
-%%% deal properly with Accept headers)
-status_moved_permanently(Method,Headers,Body,Req,Session)
- when (((Req#request.settings)#client_settings.autoredirect)==true) and
- (Method==get) or (Method==head) ->
- ServerClose=http_lib:connection_close(Headers),
- case Headers#res_headers.location of
- undefined ->
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {301,Headers,Body}}),
- handle_connection(Session#session.clientclose,ServerClose,
- Req,Session);
- RedirUrl ->
- Scheme=Session#session.scheme,
- case uri:parse(RedirUrl) of
- {error,Reason} ->
- {error,Reason};
- {Scheme,Host,Port,PathQuery} -> % Automatic redirection
- NewReq=Req#request{redircount=Req#request.redircount+1,
- address={Host,Port},pathquery=PathQuery},
- handle_redirect(Session#session.clientclose,ServerClose,
- NewReq,Session)
- end
- end;
-status_moved_permanently(_Method,Headers,Body,Req,Session) ->
- ServerClose=http_lib:connection_close(Headers),
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {301,Headers,Body}}),
- handle_connection(Session#session.clientclose,ServerClose,Req,Session).
-
-
-%%% Received a 302 Status code ("Found")
-%%% The requested resource resides temporarily under a different URI.
-%%% Note:
-%%% - Only cacheable if indicated by a Cache-Control or Expires header
-status_found(Headers,Body,Req,Session)
- when ((Req#request.settings)#client_settings.autoredirect)==true ->
- ServerClose=http_lib:connection_close(Headers),
- case Headers#res_headers.location of
- undefined ->
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {302,Headers,Body}}),
- handle_connection(Session#session.clientclose,ServerClose,
- Req,Session);
- RedirUrl ->
- Scheme=Session#session.scheme,
- case uri:parse(RedirUrl) of
- {error,Reason} ->
- {error,Reason};
- {Scheme,Host,Port,PathQuery} -> % Automatic redirection
- NewReq=Req#request{redircount=Req#request.redircount+1,
- address={Host,Port},pathquery=PathQuery},
- handle_redirect(Session#session.clientclose,ServerClose,
- NewReq,Session)
- end
- end;
-status_found(Headers,Body,Req,Session) ->
- ServerClose=http_lib:connection_close(Headers),
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {302,Headers,Body}}),
- handle_connection(Session#session.clientclose,ServerClose,Req,Session).
-
-%%% Received a 303 Status code ("See Other")
-%%% The request found under a different URI and should be retrieved using GET
-%%% Note:
-%%% - Must not be cached
-status_see_other(Headers,Body,Req,Session)
- when ((Req#request.settings)#client_settings.autoredirect)==true ->
- ServerClose=http_lib:connection_close(Headers),
- case Headers#res_headers.location of
- undefined ->
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {303,Headers,Body}}),
- handle_connection(Session#session.clientclose,ServerClose,
- Req,Session);
- RedirUrl ->
- Scheme=Session#session.scheme,
- case uri:parse(RedirUrl) of
- {error,Reason} ->
- {error,Reason};
- {Scheme,Host,Port,PathQuery} -> % Automatic redirection
- NewReq=Req#request{redircount=Req#request.redircount+1,
- method=get,
- address={Host,Port},pathquery=PathQuery},
- handle_redirect(Session#session.clientclose,ServerClose,
- NewReq,Session)
- end
- end;
-status_see_other(Headers,Body,Req,Session) ->
- ServerClose=http_lib:connection_close(Headers),
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {303,Headers,Body}}),
- handle_connection(Session#session.clientclose,ServerClose,Req,Session).
-
-
-%%% Received a 304 Status code ("Not Modified")
-%%% Note:
-%%% - The response MUST NOT contain a body.
-%%% - The response MUST include the following header fields:
-%%% - Date, unless its omission is required
-%%% - ETag and/or Content-Location, if the header would have been sent
-%%% in a 200 response to the same request
-%%% - Expires, Cache-Control, and/or Vary, if the field-value might
-%%% differ from that sent in any previous response for the same
-%%% variant
-status_not_modified(Headers,Body,Req,Session)
- when ((Req#request.settings)#client_settings.autoredirect)==true ->
- ServerClose=http_lib:connection_close(Headers),
- case Headers#res_headers.location of
- undefined ->
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {304,Headers,Body}}),
- handle_connection(Session#session.clientclose,ServerClose,
- Req,Session);
- RedirUrl ->
- Scheme=Session#session.scheme,
- case uri:parse(RedirUrl) of
- {error,Reason} ->
- {error,Reason};
- {Scheme,Host,Port,PathQuery} -> % Automatic redirection
- NewReq=Req#request{redircount=Req#request.redircount+1,
- address={Host,Port},pathquery=PathQuery},
- handle_redirect(Session#session.clientclose,ServerClose,
- NewReq,Session)
- end
- end;
-status_not_modified(Headers,Body,Req,Session) ->
- ServerClose=http_lib:connection_close(Headers),
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {304,Headers,Body}}),
- handle_connection(Session#session.clientclose,ServerClose,Req,Session).
-
-
-
-%%% Received a 305 Status code ("Use Proxy")
-%%% The requested resource MUST be accessed through the proxy given by the
-%%% Location field
-status_use_proxy(Headers,Body,Req,Session)
- when ((Req#request.settings)#client_settings.autoredirect)==true ->
- ServerClose=http_lib:connection_close(Headers),
- case Headers#res_headers.location of
- undefined ->
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {305,Headers,Body}}),
- handle_connection(Session#session.clientclose,ServerClose,
- Req,Session);
- RedirUrl ->
- Scheme=Session#session.scheme,
- case uri:parse(RedirUrl) of
- {error,Reason} ->
- {error,Reason};
- {Scheme,Host,Port,PathQuery} -> % Automatic redirection
- NewReq=Req#request{redircount=Req#request.redircount+1,
- address={Host,Port},pathquery=PathQuery},
- handle_redirect(Session#session.clientclose,ServerClose,
- NewReq,Session)
- end
- end;
-status_use_proxy(Headers,Body,Req,Session) ->
- ServerClose=http_lib:connection_close(Headers),
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {305,Headers,Body}}),
- handle_connection(Session#session.clientclose,ServerClose,Req,Session).
-
-
-%%% Received a 307 Status code ("Temporary Redirect")
-status_temporary_redirect(Headers,Body,Req,Session)
- when ((Req#request.settings)#client_settings.autoredirect)==true ->
- ServerClose=http_lib:connection_close(Headers),
- case Headers#res_headers.location of
- undefined ->
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {307,Headers,Body}}),
- handle_connection(Session#session.clientclose,ServerClose,
- Req,Session);
- RedirUrl ->
- Scheme=Session#session.scheme,
- case uri:parse(RedirUrl) of
- {error,Reason} ->
- {error,Reason};
- {Scheme,Host,Port,PathQuery} -> % Automatic redirection
- NewReq=Req#request{redircount=Req#request.redircount+1,
- address={Host,Port},pathquery=PathQuery},
- handle_redirect(Session#session.clientclose,ServerClose,
- NewReq,Session)
- end
- end;
-status_temporary_redirect(Headers,Body,Req,Session) ->
- ServerClose=http_lib:connection_close(Headers),
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {307,Headers,Body}}),
- handle_connection(Session#session.clientclose,ServerClose,Req,Session).
-
-
-
-%%% Received a 503 Status code ("Service Unavailable")
-%%% The server is currently unable to handle the request due to a
-%%% temporary overloading or maintenance of the server. The implication
-%%% is that this is a temporary condition which will be alleviated after
-%%% some delay. If known, the length of the delay MAY be indicated in a
-%%% Retry-After header. If no Retry-After is given, the client SHOULD
-%%% handle the response as it would for a 500 response.
-%% Note:
-%% - This session is now considered busy, thus cancel any requests in the
-%% pipeline and close the session.
-%% FIXME! Implement a user option to automatically retry if the 'Retry-After'
-%% header is given.
-status_service_unavailable(Resp,Req,Session) ->
-% RetryAfter=Headers#res_headers.retry_after,
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,Resp}),
- close_session(server_connection_close,Req,Session).
-
-
-%%% Received a 50x Status code (~ "Service Error")
-%%% Response status codes beginning with the digit "5" indicate cases in
-%%% which the server is aware that it has erred or is incapable of
-%%% performing the request.
-status_server_error_50x(Resp,Req,Session) ->
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,Resp}),
- close_session(server_connection_close,Req,Session).
-
-
-%%% Handles requests for redirects
-%%% The redirected request might be:
-%%% - FIXME! on another TCP session, another scheme
-%%% - on the same TCP session, same scheme
-%%% - on another TCP session , same scheme
-%%% However, in all cases treat it as a new request, with redircount updated.
-%%%
-%%% The redirect may fail, but this not a reason to close this session.
-%%% Instead return a error for this request, and continue as ok.
-handle_redirect(ClientClose,ServerClose,Req,Session) ->
- case httpc_manager:request(Req) of
- {ok,_ReqId} -> % FIXME Should I perhaps reuse the Reqid?
- handle_connection(ClientClose,ServerClose,Req,Session);
- {error,Reason} ->
- gen_server:cast(Req#request.from,{Req#request.ref,Req#request.id,
- {error,Reason}}),
- handle_connection(ClientClose,ServerClose,Req,Session)
- end.
-
-%%% Check if the persistent connection flag is false (ie client request
-%%% non-persistive connection), or if the server requires a closed connection
-%%% (by sending a "Connection: close" header). If the connection required
-%%% non-persistent, we may close the connection immediately.
-handle_connection(ClientClose,ServerClose,Req,Session) ->
- case {ClientClose,ServerClose} of
- {false,false} ->
- ok;
- {false,true} -> % The server requests this session to be closed.
- close_session(server_connection_close,Req,Session);
- {true,_} -> % The client requested a non-persistent connection
- close_session(client_connection_close,Req,Session)
- end.
-
-
-%%% Close the session.
-%%% We now have three cases:
-%%% - Client request a non-persistent connection when initiating the request.
-%%% Session info not stored in httpc_manager
-%%% - Server requests a non-persistent connection when answering a request.
-%%% No need to resend request, but there might be a pipeline.
-%%% - Some kind of error
-%%% Close the session, we may then try resending all requests in the pipeline
-%%% including the current depending on the error.
-%%% FIXME! Should not always abort the session (see close_session in
-%%% httpc_manager for more details)
-close_session(client_connection_close,_Req,Session) ->
- http_lib:close(Session#session.scheme,Session#session.socket),
- stop;
-close_session(server_connection_close,Req,Session) ->
- http_lib:close(Session#session.scheme,Session#session.socket),
- httpc_manager:abort_session(Req#request.address,Session#session.id,
- aborted_request),
- stop.
-
-exit_session(Address,Session,Reason) ->
- http_lib:close(Session#session.scheme,Session#session.socket),
- httpc_manager:abort_session(Address,Session#session.id,Reason),
- exit(normal).
-
-%%% This is the "normal" case to close a persistent connection. I.e., there are
-%%% no more requests waiting and the session was closed by the client, or
-%%% server because of a timeout or user request.
-exit_session_ok(Address,Session) ->
- http_lib:close(Session#session.scheme,Session#session.socket),
- exit_session_ok2(Address,Session#session.clientclose,Session#session.id).
-
-exit_session_ok2(Address,ClientClose,Sid) ->
- case ClientClose of
- false ->
- httpc_manager:close_session(Address,Sid);
- true ->
- ok
- end,
- exit(normal).
-
-%%% ============================================================================
-%%% This is deprecated code, to be removed
-
-format_time() ->
- {_,_,MicroSecs}=TS=now(),
- {{Y,Mon,D},{H,M,S}}=calendar:now_to_universal_time(TS),
- lists:flatten(io_lib:format("~4.4.0w-~2.2.0w-~2.2.0w,~2.2.0w:~2.2.0w:~6.3.0f",
- [Y,Mon,D,H,M,S+(MicroSecs/1000000)])).
-
-%%% Read more data from the open socket.
-%%% Two different read functions is used because for the {active, once} socket
-%%% option is (currently) not available for SSL...
-%%% FIXME
-% read_more_data(http,Socket,Timeout) ->
-% io:format("read_more_data(ip_comm) -> "
-% "~n set active = 'once' and "
-% "await a chunk data", []),
-% http_lib:setopts(Socket, [{active,once}]),
-% read_more_data_ipcomm(Socket,Timeout);
-% read_more_data(https,Socket,Timeout) ->
-% case ssl:recv(Socket,0,Timeout) of
-% {ok,MoreData} ->
-% MoreData;
-% {error,closed} ->
-% throw({error, session_remotely_closed});
-% {error,etimedout} ->
-% throw({error, session_local_timeout});
-% {error,Reason} ->
-% throw({error, Reason});
-% Other ->
-% throw({error, Other})
-% end.
-
-% %%% Send any incoming requests on the open session immediately
-% read_more_data_ipcomm(Socket,Timeout) ->
-% receive
-% {tcp,Socket,MoreData} ->
-% % ?vtrace("read_more_data(ip_comm) -> got some data:~p",
-% % [MoreData]),
-% MoreData;
-% {tcp_closed,Socket} ->
-% % ?vtrace("read_more_data(ip_comm) -> socket closed",[]),
-% throw({error,session_remotely_closed});
-% {tcp_error,Socket,Reason} ->
-% % ?vtrace("read_more_data(ip_comm) -> ~p socket error: ~p",
-% % [self(),Reason]),
-% throw({error, Reason});
-% stop ->
-% throw({error, user_req})
-% after Timeout ->
-% throw({error, session_local_timeout})
-% end.