Merge remote-tracking branch 'jocelynEWF/master'

This commit is contained in:
jvelilla
2011-09-16 07:04:40 -03:00
60 changed files with 913 additions and 485 deletions

View File

@@ -1,5 +1,5 @@
Official project site for Eiffel Web Framework: Official project site for Eiffel Web Framework:
* https://github.com/Eiffel-World/Eiffel-Web-Framework * http://eiffel-world.github.com/Eiffel-Web-Framework/
For more information please have a look at the related wiki: For more information please have a look at the related wiki:
* https://github.com/Eiffel-World/Eiffel-Web-Framework/wiki * https://github.com/Eiffel-World/Eiffel-Web-Framework/wiki
@@ -20,6 +20,9 @@ Overview
* library/server/ewsgi/connectors: various web server connectors for EWSGI * library/server/ewsgi/connectors: various web server connectors for EWSGI
* library/server/libfcgi: Wrapper for libfcgi SDK * library/server/libfcgi: Wrapper for libfcgi SDK
* library/server/request/router: URL dispatching/routing based on uri, uri_template, or custom.
* library/server/request/rest: experimental: RESTful library to help building RESTful services
* library/protocol/http: HTTP related classes, constants for status code, content types, ... * library/protocol/http: HTTP related classes, constants for status code, content types, ...
* library/protocol/uri_template: URI Template library (parsing and expander) * library/protocol/uri_template: URI Template library (parsing and expander)

View File

@@ -10,7 +10,7 @@ class
inherit inherit
ANY ANY
DEFAULT_URI_TEMPLATE_ROUTED_APPLICATION URI_TEMPLATE_ROUTED_APPLICATION
ROUTED_APPLICATION_HELPER ROUTED_APPLICATION_HELPER
@@ -36,7 +36,7 @@ feature {NONE} -- Initialization
setup_router setup_router
local local
ra: REQUEST_AGENT_HANDLER [REQUEST_URI_TEMPLATE_HANDLER_CONTEXT] ra: REQUEST_AGENT_HANDLER [REQUEST_URI_TEMPLATE_HANDLER_CONTEXT]
rag: DEFAULT_REQUEST_URI_TEMPLATE_ROUTING_HANDLER rag: REQUEST_URI_TEMPLATE_ROUTING_HANDLER
do do
router.map_agent ("/home", agent execute_home) router.map_agent ("/home", agent execute_home)
@@ -126,8 +126,8 @@ feature -- Execution
res.write_string ("<li><a href=%""+ req.script_url ("/hello/Joce") + "%">/hello/Joce</a></li>%N") res.write_string ("<li><a href=%""+ req.script_url ("/hello/Joce") + "%">/hello/Joce</a></li>%N")
res.write_string ("</ul>%N") res.write_string ("</ul>%N")
if attached req.parameter ("REQUEST_COUNT") as rqc then if attached req.item ("REQUEST_COUNT") as rqc then
res.write_string ("request #"+ rqc + "%N") res.write_string ("request #"+ rqc.as_string + "%N")
end end
res.write_string ("</body></html>%N") res.write_string ("</body></html>%N")
end end
@@ -183,7 +183,7 @@ feature -- Execution
handle_anonymous_hello (ctx: REQUEST_URI_TEMPLATE_HANDLER_CONTEXT; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER) handle_anonymous_hello (ctx: REQUEST_URI_TEMPLATE_HANDLER_CONTEXT; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
do do
execute_hello (req, res, ctx.parameter ("name"), ctx) execute_hello (req, res, ctx.string_parameter ("name"), ctx)
end end
handle_method_any (ctx: REQUEST_URI_TEMPLATE_HANDLER_CONTEXT; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER) handle_method_any (ctx: REQUEST_URI_TEMPLATE_HANDLER_CONTEXT; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)

View File

@@ -58,7 +58,7 @@ feature -- Query
feature -- Query: url-decoded feature -- Query: url-decoded
url_decoded_query_variable (n: READABLE_STRING_GENERAL): detachable STRING_32 url_decoded_query_variable (n: READABLE_STRING_GENERAL): detachable READABLE_STRING_32
-- Unencoded value related to variable name `n' -- Unencoded value related to variable name `n'
do do
if attached query_variable (n) as v then if attached query_variable (n) as v then
@@ -66,7 +66,7 @@ feature -- Query: url-decoded
end end
end end
url_decoded_path_variable (n: READABLE_STRING_GENERAL): detachable STRING_32 url_decoded_path_variable (n: READABLE_STRING_GENERAL): detachable READABLE_STRING_32
-- Unencoded value related to variable name `n' -- Unencoded value related to variable name `n'
do do
if attached path_variable (n) as v then if attached path_variable (n) as v then
@@ -74,7 +74,7 @@ feature -- Query: url-decoded
end end
end end
url_decoded_variable (n: READABLE_STRING_GENERAL): detachable STRING_32 url_decoded_variable (n: READABLE_STRING_GENERAL): detachable READABLE_STRING_32
-- Unencoded value related to variable name `n' -- Unencoded value related to variable name `n'
do do
if attached variable (n) as v then if attached variable (n) as v then
@@ -84,7 +84,7 @@ feature -- Query: url-decoded
feature {NONE} -- Implementation feature {NONE} -- Implementation
url_decoded_string (s: READABLE_STRING_GENERAL): STRING_32 url_decoded_string (s: READABLE_STRING_GENERAL): READABLE_STRING_32
do do
Result := url_encoder.decoded_string (s.as_string_8) Result := url_encoder.decoded_string (s.as_string_8)
end end

View File

@@ -78,7 +78,7 @@ feature -- Server
do do
create req.make (env, create {EWF_NINO_INPUT_STREAM}.make (a_input)) create req.make (env, create {EWF_NINO_INPUT_STREAM}.make (a_input))
create res.make (create {EWF_NINO_OUTPUT_STREAM}.make (a_output)) create res.make (create {EWF_NINO_OUTPUT_STREAM}.make (a_output))
req.set_meta_variable ("RAW_HEADER_DATA", a_headers_text) req.set_meta_string_variable ("RAW_HEADER_DATA", a_headers_text)
application.execute (req, res) application.execute (req, res)
end end

View File

@@ -0,0 +1,122 @@
note
description: "Summary description for {WGI_MULTIPLE_STRING_VALUE}."
author: ""
date: "$Date$"
revision: "$Revision$"
class
WGI_MULTIPLE_STRING_VALUE
inherit
WGI_VALUE
ITERABLE [WGI_STRING_VALUE]
create
make_with_value,
make_with_string
feature {NONE} -- Initialization
make_with_value (a_value: WGI_VALUE)
do
name := a_value.name
create {LINKED_LIST [WGI_STRING_VALUE]} string_values.make
add_value (a_value)
end
make_with_string (a_name: like name; a_string: READABLE_STRING_32)
do
make_with_value (create {WGI_STRING_VALUE}.make (a_name, a_string))
end
feature -- Access
name: READABLE_STRING_GENERAL
string_values: LIST [WGI_STRING_VALUE]
first_string_value: WGI_STRING_VALUE
do
Result := string_values.first
end
feature -- Traversing
new_cursor: ITERATION_CURSOR [WGI_STRING_VALUE]
do
Result := string_values.new_cursor
end
feature -- Helper
same_string (a_other: READABLE_STRING_GENERAL): BOOLEAN
-- Does `a_other' represent the same string as `Current'?
do
if string_values.count = 1 then
Result := first_string_value.same_string (a_other)
end
end
is_case_insensitive_equal (a_other: READABLE_STRING_8): BOOLEAN
-- Does `a_other' represent the same case insensitive string as `Current'?
do
if string_values.count = 1 then
Result := first_string_value.is_case_insensitive_equal (a_other)
end
end
as_string: STRING_32
do
if string_values.count = 1 then
create Result.make_from_string (first_string_value)
else
create Result.make_from_string ("[")
across
string_values as c
loop
if Result.count = 1 then
Result.append_character (',')
end
Result.append_string (c.item)
end
Result.append_character (']')
end
end
feature -- Element change
add_value (a_value: WGI_VALUE)
require
same_name: a_value.name.same_string (name)
do
if attached {WGI_STRING_VALUE} a_value as sval then
add_string_value (sval)
elseif attached {WGI_MULTIPLE_STRING_VALUE} a_value as slst then
across
slst as cur
loop
add_string_value (cur.item)
end
end
end
add_string_value (s: WGI_STRING_VALUE)
do
string_values.extend (s)
end
invariant
string_values_not_empty: string_values.count >= 1
;note
copyright: "2011-2011, Eiffel Software and others"
license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)"
source: "[
Eiffel Software
5949 Hollister Ave., Goleta, CA 93117 USA
Telephone 805-685-1006, Fax 805-685-6869
Website http://www.eiffel.com
Customer support http://support.eiffel.com
]"
end

View File

@@ -0,0 +1,71 @@
note
description: "Summary description for {WGI_STRING_VALUE}."
author: ""
date: "$Date$"
revision: "$Revision$"
class
WGI_STRING_VALUE
inherit
WGI_VALUE
create
make
convert
as_string: {READABLE_STRING_32, STRING_32}
feature {NONE} -- Initialization
make (a_name: like name; a_string: like string)
do
name := a_name
string := a_string
end
feature -- Access
name: READABLE_STRING_GENERAL
string: READABLE_STRING_32
feature -- Helper
same_string (a_other: READABLE_STRING_GENERAL): BOOLEAN
-- Does `a_other' represent the same string as `Current'?
do
Result := string.same_string_general (a_other)
end
is_case_insensitive_equal (a_other: READABLE_STRING_8): BOOLEAN
-- Does `a_other' represent the same case insensitive string as `Current'?
local
v: like string
do
v := string
if v = a_other then
Result := True
elseif v.is_valid_as_string_8 then
Result := v.is_case_insensitive_equal (a_other)
end
end
feature -- Conversion
as_string: STRING_32
do
create Result.make_from_string (string)
end
;note
copyright: "2011-2011, Eiffel Software and others"
license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)"
source: "[
Eiffel Software
5949 Hollister Ave., Goleta, CA 93117 USA
Telephone 805-685-1006, Fax 805-685-6869
Website http://www.eiffel.com
Customer support http://support.eiffel.com
]"
end

View File

@@ -89,14 +89,14 @@ feature -- Access: extra values
feature -- Access: CGI meta variables feature -- Access: CGI meta variables
meta_variable (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 meta_variable (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
-- Environment variable related to `a_name' -- Environment variable related to `a_name'
require require
a_name_valid: a_name /= Void and then not a_name.is_empty a_name_valid: a_name /= Void and then not a_name.is_empty
deferred deferred
end end
meta_variables: HASH_TABLE [READABLE_STRING_32, READABLE_STRING_GENERAL] meta_variables: ITERATION_CURSOR [WGI_VALUE]
-- These variables are specific to requests made with HTTP. -- These variables are specific to requests made with HTTP.
-- Interpretation of these variables may depend on the value of -- Interpretation of these variables may depend on the value of
-- SERVER_PROTOCOL. -- SERVER_PROTOCOL.
@@ -575,28 +575,14 @@ feature -- Extra CGI environment variables
deferred deferred
end end
--feature -- Access: execution variables
-- execution_variables: WGI_VARIABLES [STRING_32]
-- -- Execution variables set by the application
-- deferred
-- end
-- execution_variable (a_name: STRING): detachable STRING_32
-- -- Execution variable related to `a_name'
-- require
-- a_name_valid: a_name /= Void and then not a_name.is_empty
-- deferred
-- end
feature -- Query string Parameters feature -- Query string Parameters
query_parameters: HASH_TABLE [READABLE_STRING_32, READABLE_STRING_GENERAL] query_parameters: ITERATION_CURSOR [WGI_VALUE]
-- Variables extracted from QUERY_STRING -- Variables extracted from QUERY_STRING
deferred deferred
end end
query_parameter (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 query_parameter (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
-- Parameter for name `n'. -- Parameter for name `n'.
require require
a_name_valid: a_name /= Void and then not a_name.is_empty a_name_valid: a_name /= Void and then not a_name.is_empty
@@ -605,12 +591,12 @@ feature -- Query string Parameters
feature -- Form fields and related feature -- Form fields and related
form_data_parameters: HASH_TABLE [READABLE_STRING_32, READABLE_STRING_GENERAL] form_data_parameters: ITERATION_CURSOR [WGI_VALUE]
-- Variables sent by POST request -- Variables sent by POST request
deferred deferred
end end
form_data_parameter (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 form_data_parameter (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
-- Field for name `a_name'. -- Field for name `a_name'.
require require
a_name_valid: a_name /= Void and then not a_name.is_empty a_name_valid: a_name /= Void and then not a_name.is_empty
@@ -630,12 +616,12 @@ feature -- Form fields and related
feature -- Cookies feature -- Cookies
cookies: HASH_TABLE [READABLE_STRING_32, READABLE_STRING_GENERAL] cookies: ITERATION_CURSOR [WGI_VALUE]
-- Expanded cookies variable -- Expanded cookies variable
deferred deferred
end end
cookie (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 cookie (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
-- Field for name `a_name'. -- Field for name `a_name'.
require require
a_name_valid: a_name /= Void and then not a_name.is_empty a_name_valid: a_name /= Void and then not a_name.is_empty
@@ -644,14 +630,26 @@ feature -- Cookies
feature -- Access: global variable feature -- Access: global variable
parameters: HASH_TABLE [READABLE_STRING_32, READABLE_STRING_GENERAL] parameters: like items
obsolete "use items"
do
Result := items
end
parameter (a_name: READABLE_STRING_GENERAL): like item
obsolete "use item"
do
Result := item (a_name)
end
items: ITERATION_CURSOR [WGI_VALUE]
-- Table containing all the various variables -- Table containing all the various variables
-- Warning: this is computed each time, if you change the content of other containers -- Warning: this is computed each time, if you change the content of other containers
-- this won't update this Result's content, unless you query it again -- this won't update this Result's content, unless you query it again
deferred deferred
end end
parameter (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 item (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
-- Variable named `a_name' from any of the variables container -- Variable named `a_name' from any of the variables container
-- and following a specific order -- and following a specific order
-- execution, environment, get, post, cookies -- execution, environment, get, post, cookies

View File

@@ -0,0 +1,48 @@
note
description: "Summary description for {WGI_VALUE}."
author: ""
date: "$Date$"
revision: "$Revision$"
deferred class
WGI_VALUE
convert
as_string: {READABLE_STRING_32, STRING_32}
feature -- Access
name: READABLE_STRING_GENERAL
-- Parameter name
deferred
end
feature -- Helper
same_string (a_other: READABLE_STRING_GENERAL): BOOLEAN
-- Does `a_other' represent the same string as `Current'?
deferred
end
is_case_insensitive_equal (a_other: READABLE_STRING_8): BOOLEAN
-- Does `a_other' represent the same case insensitive string as `Current'?
deferred
end
feature -- Query
as_string: STRING_32
deferred
end
note
copyright: "2011-2011, Eiffel Software and others"
license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)"
source: "[
Eiffel Software
5949 Hollister Ave., Goleta, CA 93117 USA
Telephone 805-685-1006, Fax 805-685-6869
Website http://www.eiffel.com
Customer support http://support.eiffel.com
]"
end

View File

@@ -34,33 +34,33 @@ feature {NONE} -- Initialization
analyze analyze
end end
set_meta_parameters (a_vars: HASH_TABLE [READABLE_STRING_8, READABLE_STRING_8]) set_meta_parameters (a_vars: HASH_TABLE [READABLE_STRING_8, READABLE_STRING_GENERAL])
-- Fill with variable from `a_vars' -- Fill with variable from `a_vars'
local local
s: like meta_variable s: like meta_string_variable
table: HASH_TABLE [READABLE_STRING_32, READABLE_STRING_GENERAL] table: HASH_TABLE [WGI_VALUE, READABLE_STRING_GENERAL]
do do
create {STRING_32} empty_string.make_empty create {STRING_32} empty_string.make_empty
create table.make (a_vars.count) create table.make (a_vars.count)
meta_variables := table meta_variables_table := table
from from
a_vars.start a_vars.start
until until
a_vars.after a_vars.after
loop loop
table.force (a_vars.item_for_iteration, a_vars.key_for_iteration) table.force (new_string_value (a_vars.key_for_iteration, a_vars.item_for_iteration), a_vars.key_for_iteration)
a_vars.forth a_vars.forth
end end
--| QUERY_STRING --| QUERY_STRING
query_string := meta_parameter_or_default ({WGI_META_NAMES}.query_string, empty_string, False) query_string := meta_string_variable_or_default ({WGI_META_NAMES}.query_string, empty_string, False)
--| REQUEST_METHOD --| REQUEST_METHOD
request_method := meta_parameter_or_default ({WGI_META_NAMES}.request_method, empty_string, False) request_method := meta_string_variable_or_default ({WGI_META_NAMES}.request_method, empty_string, False)
--| CONTENT_TYPE --| CONTENT_TYPE
s := meta_variable ({WGI_META_NAMES}.content_type) s := meta_string_variable ({WGI_META_NAMES}.content_type)
if s /= Void and then not s.is_empty then if s /= Void and then not s.is_empty then
content_type := s content_type := s
else else
@@ -68,7 +68,7 @@ feature {NONE} -- Initialization
end end
--| CONTENT_LENGTH --| CONTENT_LENGTH
s := meta_variable ({WGI_META_NAMES}.content_length) s := meta_string_variable ({WGI_META_NAMES}.content_length)
content_length := s content_length := s
if s /= Void and then s.is_natural_64 then if s /= Void and then s.is_natural_64 then
content_length_value := s.to_natural_64 content_length_value := s.to_natural_64
@@ -77,13 +77,13 @@ feature {NONE} -- Initialization
end end
--| PATH_INFO --| PATH_INFO
path_info := meta_parameter_or_default ({WGI_META_NAMES}.path_info, empty_string, False) path_info := meta_string_variable_or_default ({WGI_META_NAMES}.path_info, empty_string, False)
--| SERVER_NAME --| SERVER_NAME
server_name := meta_parameter_or_default ({WGI_META_NAMES}.server_name, empty_string, False) server_name := meta_string_variable_or_default ({WGI_META_NAMES}.server_name, empty_string, False)
--| SERVER_PORT --| SERVER_PORT
s := meta_variable ({WGI_META_NAMES}.server_port) s := meta_string_variable ({WGI_META_NAMES}.server_port)
if s /= Void and then s.is_integer then if s /= Void and then s.is_integer then
server_port := s.to_integer server_port := s.to_integer
else else
@@ -91,16 +91,16 @@ feature {NONE} -- Initialization
end end
--| SCRIPT_NAME --| SCRIPT_NAME
script_name := meta_parameter_or_default ({WGI_META_NAMES}.script_name, empty_string, False) script_name := meta_string_variable_or_default ({WGI_META_NAMES}.script_name, empty_string, False)
--| REMOTE_ADDR --| REMOTE_ADDR
remote_addr := meta_parameter_or_default ({WGI_META_NAMES}.remote_addr, empty_string, False) remote_addr := meta_string_variable_or_default ({WGI_META_NAMES}.remote_addr, empty_string, False)
--| REMOTE_HOST --| REMOTE_HOST
remote_host := meta_parameter_or_default ({WGI_META_NAMES}.remote_host, empty_string, False) remote_host := meta_string_variable_or_default ({WGI_META_NAMES}.remote_host, empty_string, False)
--| REQUEST_URI --| REQUEST_URI
request_uri := meta_parameter_or_default ({WGI_META_NAMES}.request_uri, empty_string, False) request_uri := meta_string_variable_or_default ({WGI_META_NAMES}.request_uri, empty_string, False)
end end
initialize initialize
@@ -114,13 +114,13 @@ feature {NONE} -- Initialization
if attached request_uri as rq_uri then if attached request_uri as rq_uri then
p := rq_uri.index_of ('?', 1) p := rq_uri.index_of ('?', 1)
if p > 0 then if p > 0 then
set_meta_variable (rq_uri.substring (1, p-1), {WGI_META_NAMES}.self) set_meta_string_variable (rq_uri.substring (1, p-1), {WGI_META_NAMES}.self)
else else
set_meta_variable (rq_uri, {WGI_META_NAMES}.self) set_meta_string_variable (rq_uri, {WGI_META_NAMES}.self)
end end
end end
if meta_variable ({WGI_META_NAMES}.request_time) = Void then if meta_variable ({WGI_META_NAMES}.request_time) = Void then
set_meta_variable (date_time_utilities.unix_time_stamp (Void).out, {WGI_META_NAMES}.request_time) set_meta_string_variable (date_time_utilities.unix_time_stamp (Void).out, {WGI_META_NAMES}.request_time)
end end
end end
@@ -160,51 +160,65 @@ feature -- Access extra information
-- Request time (UTC) -- Request time (UTC)
do do
if if
attached meta_variable ({WGI_META_NAMES}.request_time) as t and then attached {WGI_STRING_VALUE} meta_variable ({WGI_META_NAMES}.request_time) as t and then
t.is_integer_64 t.string.is_integer_64
then then
Result := date_time_utilities.unix_time_stamp_to_date_time (t.to_integer_64) Result := date_time_utilities.unix_time_stamp_to_date_time (t.string.to_integer_64)
end end
end end
feature -- Access: CGI meta parameters feature {NONE} -- Access: CGI meta parameters
meta_variables: HASH_TABLE [READABLE_STRING_32, READABLE_STRING_GENERAL] meta_variables_table: HASH_TABLE [WGI_VALUE, READABLE_STRING_GENERAL]
-- CGI Environment parameters -- CGI Environment parameters
meta_variable (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 feature -- Access: CGI meta parameters
-- CGI meta variable related to `a_name'
meta_variables: ITERATION_CURSOR [WGI_VALUE]
do do
Result := meta_variables.item (a_name) Result := meta_variables_table.new_cursor
end end
meta_parameter_or_default (a_name: READABLE_STRING_GENERAL; a_default: READABLE_STRING_32; use_default_when_empty: BOOLEAN): READABLE_STRING_32 meta_variable (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
-- CGI meta variable related to `a_name'
do
Result := meta_variables_table.item (a_name)
end
meta_string_variable (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32
-- CGI meta variable related to `a_name'
do
if attached meta_variables_table.item (a_name) as val then
Result := val.as_string
end
end
meta_string_variable_or_default (a_name: READABLE_STRING_GENERAL; a_default: READABLE_STRING_32; use_default_when_empty: BOOLEAN): READABLE_STRING_32
-- Value for meta parameter `a_name' -- Value for meta parameter `a_name'
-- If not found, return `a_default' -- If not found, return `a_default'
require require
a_name_not_empty: a_name /= Void and then not a_name.is_empty a_name_not_empty: a_name /= Void and then not a_name.is_empty
do do
if attached meta_variable (a_name) as s then if attached meta_variable (a_name) as val then
if use_default_when_empty and then s.is_empty then Result := val.as_string
if use_default_when_empty and then Result.is_empty then
Result := a_default Result := a_default
else
Result := s
end end
else else
Result := a_default Result := a_default
end end
end end
set_meta_variable (a_name: READABLE_STRING_GENERAL; a_value: READABLE_STRING_32) set_meta_string_variable (a_name: READABLE_STRING_GENERAL; a_value: READABLE_STRING_32)
do do
meta_variables.force (a_value, a_name) meta_variables_table.force (new_string_value (a_name, a_value), a_name)
ensure ensure
param_set: meta_variable (a_name) ~ a_value param_set: attached {WGI_STRING_VALUE} meta_variable (a_name) as val and then val ~ a_value
end end
unset_meta_variable (a_name: READABLE_STRING_GENERAL) unset_meta_variable (a_name: READABLE_STRING_GENERAL)
do do
meta_variables.remove (a_name) meta_variables_table.remove (a_name)
ensure ensure
param_unset: meta_variable (a_name) = Void param_unset: meta_variable (a_name) = Void
end end
@@ -221,7 +235,7 @@ feature -- Access: CGI meta parameters - 1.1
gateway_interface: READABLE_STRING_32 gateway_interface: READABLE_STRING_32
do do
Result := meta_parameter_or_default ({WGI_META_NAMES}.gateway_interface, "", False) Result := meta_string_variable_or_default ({WGI_META_NAMES}.gateway_interface, "", False)
end end
path_info: READABLE_STRING_32 path_info: READABLE_STRING_32
@@ -234,7 +248,7 @@ feature -- Access: CGI meta parameters - 1.1
path_translated: detachable READABLE_STRING_32 path_translated: detachable READABLE_STRING_32
do do
Result := meta_variable ({WGI_META_NAMES}.path_translated) Result := meta_string_variable ({WGI_META_NAMES}.path_translated)
end end
query_string: READABLE_STRING_32 query_string: READABLE_STRING_32
@@ -245,12 +259,12 @@ feature -- Access: CGI meta parameters - 1.1
remote_ident: detachable READABLE_STRING_32 remote_ident: detachable READABLE_STRING_32
do do
Result := meta_variable ({WGI_META_NAMES}.remote_ident) Result := meta_string_variable ({WGI_META_NAMES}.remote_ident)
end end
remote_user: detachable READABLE_STRING_32 remote_user: detachable READABLE_STRING_32
do do
Result := meta_variable ({WGI_META_NAMES}.remote_user) Result := meta_string_variable ({WGI_META_NAMES}.remote_user)
end end
request_method: READABLE_STRING_32 request_method: READABLE_STRING_32
@@ -263,12 +277,12 @@ feature -- Access: CGI meta parameters - 1.1
server_protocol: READABLE_STRING_32 server_protocol: READABLE_STRING_32
do do
Result := meta_parameter_or_default ({WGI_META_NAMES}.server_protocol, "HTTP/1.0", True) Result := meta_string_variable_or_default ({WGI_META_NAMES}.server_protocol, "HTTP/1.0", True)
end end
server_software: READABLE_STRING_32 server_software: READABLE_STRING_32
do do
Result := meta_parameter_or_default ({WGI_META_NAMES}.server_software, "Unknown Server", True) Result := meta_string_variable_or_default ({WGI_META_NAMES}.server_software, "Unknown Server", True)
end end
feature -- Access: HTTP_* CGI meta parameters - 1.1 feature -- Access: HTTP_* CGI meta parameters - 1.1
@@ -276,41 +290,41 @@ feature -- Access: HTTP_* CGI meta parameters - 1.1
http_accept: detachable READABLE_STRING_32 http_accept: detachable READABLE_STRING_32
-- Contents of the Accept: header from the current request, if there is one. -- Contents of the Accept: header from the current request, if there is one.
do do
Result := meta_variable ({WGI_META_NAMES}.http_accept) Result := meta_string_variable ({WGI_META_NAMES}.http_accept)
end end
http_accept_charset: detachable READABLE_STRING_32 http_accept_charset: detachable READABLE_STRING_32
-- Contents of the Accept-Charset: header from the current request, if there is one. -- Contents of the Accept-Charset: header from the current request, if there is one.
-- Example: 'iso-8859-1,*,utf-8'. -- Example: 'iso-8859-1,*,utf-8'.
do do
Result := meta_variable ({WGI_META_NAMES}.http_accept_charset) Result := meta_string_variable ({WGI_META_NAMES}.http_accept_charset)
end end
http_accept_encoding: detachable READABLE_STRING_32 http_accept_encoding: detachable READABLE_STRING_32
-- Contents of the Accept-Encoding: header from the current request, if there is one. -- Contents of the Accept-Encoding: header from the current request, if there is one.
-- Example: 'gzip'. -- Example: 'gzip'.
do do
Result := meta_variable ({WGI_META_NAMES}.http_accept_encoding) Result := meta_string_variable ({WGI_META_NAMES}.http_accept_encoding)
end end
http_accept_language: detachable READABLE_STRING_32 http_accept_language: detachable READABLE_STRING_32
-- Contents of the Accept-Language: header from the current request, if there is one. -- Contents of the Accept-Language: header from the current request, if there is one.
-- Example: 'en'. -- Example: 'en'.
do do
Result := meta_variable ({WGI_META_NAMES}.http_accept_language) Result := meta_string_variable ({WGI_META_NAMES}.http_accept_language)
end end
http_connection: detachable READABLE_STRING_32 http_connection: detachable READABLE_STRING_32
-- Contents of the Connection: header from the current request, if there is one. -- Contents of the Connection: header from the current request, if there is one.
-- Example: 'Keep-Alive'. -- Example: 'Keep-Alive'.
do do
Result := meta_variable ({WGI_META_NAMES}.http_connection) Result := meta_string_variable ({WGI_META_NAMES}.http_connection)
end end
http_host: detachable READABLE_STRING_32 http_host: detachable READABLE_STRING_32
-- Contents of the Host: header from the current request, if there is one. -- Contents of the Host: header from the current request, if there is one.
do do
Result := meta_variable ({WGI_META_NAMES}.http_host) Result := meta_string_variable ({WGI_META_NAMES}.http_host)
end end
http_referer: detachable READABLE_STRING_32 http_referer: detachable READABLE_STRING_32
@@ -319,7 +333,7 @@ feature -- Access: HTTP_* CGI meta parameters - 1.1
-- Not all user agents will set this, and some provide the ability to modify HTTP_REFERER as a feature. -- Not all user agents will set this, and some provide the ability to modify HTTP_REFERER as a feature.
-- In short, it cannot really be trusted. -- In short, it cannot really be trusted.
do do
Result := meta_variable ({WGI_META_NAMES}.http_referer) Result := meta_string_variable ({WGI_META_NAMES}.http_referer)
end end
http_user_agent: detachable READABLE_STRING_32 http_user_agent: detachable READABLE_STRING_32
@@ -329,13 +343,13 @@ feature -- Access: HTTP_* CGI meta parameters - 1.1
-- Among other things, you can use this value to tailor your page's -- Among other things, you can use this value to tailor your page's
-- output to the capabilities of the user agent. -- output to the capabilities of the user agent.
do do
Result := meta_variable ({WGI_META_NAMES}.http_user_agent) Result := meta_string_variable ({WGI_META_NAMES}.http_user_agent)
end end
http_authorization: detachable READABLE_STRING_32 http_authorization: detachable READABLE_STRING_32
-- Contents of the Authorization: header from the current request, if there is one. -- Contents of the Authorization: header from the current request, if there is one.
do do
Result := meta_variable ({WGI_META_NAMES}.http_authorization) Result := meta_string_variable ({WGI_META_NAMES}.http_authorization)
end end
feature -- Access: Extension to CGI meta parameters - 1.1 feature -- Access: Extension to CGI meta parameters - 1.1
@@ -354,7 +368,7 @@ feature {NONE} -- Element change: CGI meta parameter related to PATH_INFO
s_attached: s /= Void s_attached: s /= Void
do do
orig_path_info := s orig_path_info := s
set_meta_variable ({WGI_META_NAMES}.orig_path_info, s) set_meta_string_variable ({WGI_META_NAMES}.orig_path_info, s)
end end
unset_orig_path_info unset_orig_path_info
@@ -389,17 +403,17 @@ feature {NONE} -- Element change: CGI meta parameter related to PATH_INFO
end end
end end
feature -- Query parameters feature {NONE} -- Query parameters
query_parameters: HASH_TABLE [READABLE_STRING_32, READABLE_STRING_GENERAL] query_parameters_table: HASH_TABLE [WGI_VALUE, READABLE_STRING_GENERAL]
-- Variables extracted from QUERY_STRING -- Variables extracted from QUERY_STRING
local local
vars: like internal_query_parameters vars: like internal_query_parameters_table
p,e: INTEGER p,e: INTEGER
rq_uri: like request_uri rq_uri: like request_uri
s: detachable STRING s: detachable STRING
do do
vars := internal_query_parameters vars := internal_query_parameters_table
if vars = Void then if vars = Void then
s := query_string s := query_string
if s = Void then if s = Void then
@@ -416,20 +430,27 @@ feature -- Query parameters
end end
end end
vars := urlencoded_parameters (s, True) vars := urlencoded_parameters (s, True)
internal_query_parameters := vars internal_query_parameters_table := vars
end end
Result := vars Result := vars
end end
query_parameter (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 feature -- Query parameters
query_parameters: ITERATION_CURSOR [WGI_VALUE]
do
Result := query_parameters_table.new_cursor
end
query_parameter (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
-- Parameter for name `n'. -- Parameter for name `n'.
do do
Result := query_parameters.item (a_name) Result := query_parameters_table.item (a_name)
end end
feature {NONE} -- Query parameters: implementation feature {NONE} -- Query parameters: implementation
urlencoded_parameters (a_content: detachable READABLE_STRING_8; decoding: BOOLEAN): HASH_TABLE [READABLE_STRING_32, STRING] urlencoded_parameters (a_content: detachable READABLE_STRING_8; decoding: BOOLEAN): HASH_TABLE [WGI_VALUE, STRING]
-- Import `a_content' -- Import `a_content'
local local
n, p, i, j: INTEGER n, p, i, j: INTEGER
@@ -466,7 +487,7 @@ feature {NONE} -- Query parameters: implementation
l_name := url_encoder.decoded_string (l_name) l_name := url_encoder.decoded_string (l_name)
l_value := url_encoder.decoded_string (l_value) l_value := url_encoder.decoded_string (l_value)
end end
Result.force (l_value, l_name) Result.force (new_string_value (l_name, l_value), l_name)
end end
end end
end end
@@ -474,17 +495,17 @@ feature {NONE} -- Query parameters: implementation
end end
end end
feature -- Form fields and related feature {NONE} -- Form fields and related
form_data_parameters: HASH_TABLE [READABLE_STRING_32, READABLE_STRING_GENERAL] form_data_parameters_table: HASH_TABLE [WGI_VALUE, READABLE_STRING_GENERAL]
-- Variables sent by POST request -- Variables sent by POST request
local local
vars: like internal_form_data_parameters vars: like internal_form_data_parameters_table
s: STRING s: STRING
n: NATURAL_64 n: NATURAL_64
l_type: like content_type l_type: like content_type
do do
vars := internal_form_data_parameters vars := internal_form_data_parameters_table
if vars = Void then if vars = Void then
n := content_length_value n := content_length_value
if n > 0 then if n > 0 then
@@ -502,20 +523,27 @@ feature -- Form fields and related
vars := urlencoded_parameters (s, True) vars := urlencoded_parameters (s, True)
end end
if raw_post_data_recorded then if raw_post_data_recorded then
vars.force (s, "RAW_POST_DATA") vars.force (new_string_value ("RAW_POST_DATA", s), "RAW_POST_DATA")
end end
else else
create vars.make (0) create vars.make (0)
end end
internal_form_data_parameters := vars internal_form_data_parameters_table := vars
end end
Result := vars Result := vars
end end
form_data_parameter (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 feature -- Form fields and related
form_data_parameters: ITERATION_CURSOR [WGI_VALUE]
do
Result := form_data_parameters_table.new_cursor
end
form_data_parameter (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
-- Field for name `a_name'. -- Field for name `a_name'.
do do
Result := form_data_parameters.item (a_name) Result := form_data_parameters_table.item (a_name)
end end
uploaded_files: HASH_TABLE [WGI_UPLOADED_FILE_DATA, STRING] uploaded_files: HASH_TABLE [WGI_UPLOADED_FILE_DATA, STRING]
@@ -527,18 +555,19 @@ feature -- Form fields and related
--| error: if /= 0 , there was an error : TODO ... --| error: if /= 0 , there was an error : TODO ...
--| size: size of the file given by the http request --| size: size of the file given by the http request
feature -- Cookies feature {NONE} -- Cookies
cookies: HASH_TABLE [READABLE_STRING_32, READABLE_STRING_GENERAL] cookies_table: HASH_TABLE [WGI_VALUE, READABLE_STRING_GENERAL]
-- Expanded cookies variable -- Expanded cookies variable
local local
i,j,p,n: INTEGER i,j,p,n: INTEGER
l_cookies: like internal_cookies l_cookies: like internal_cookies_table
k,v: STRING k,v,s: STRING
do do
l_cookies := internal_cookies l_cookies := internal_cookies_table
if l_cookies = Void then if l_cookies = Void then
if attached meta_variable ({WGI_META_NAMES}.http_cookie) as s then if attached {WGI_STRING_VALUE} meta_variable ({WGI_META_NAMES}.http_cookie) as val then
s := val.string
create l_cookies.make (5) create l_cookies.make (5)
from from
n := s.count n := s.count
@@ -561,94 +590,117 @@ feature -- Cookies
v := s.substring (i + 1, j - 1) v := s.substring (i + 1, j - 1)
p := j + 1 p := j + 1
end end
l_cookies.force (v, k) l_cookies.force (new_string_value (k, v), k)
end end
end end
else else
create l_cookies.make (0) create l_cookies.make (0)
end end
internal_cookies := l_cookies internal_cookies_table := l_cookies
end end
Result := l_cookies Result := l_cookies
end end
cookie (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 feature -- Cookies
-- Field for name `a_name'.
cookies: ITERATION_CURSOR [WGI_VALUE]
do do
Result := cookies.item (a_name) Result := cookies_table.new_cursor
end end
feature -- Access: global variable cookie (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
-- Field for name `a_name'.
do
Result := cookies_table.item (a_name)
end
parameters: HASH_TABLE [READABLE_STRING_32, READABLE_STRING_GENERAL] feature {NONE} -- Access: global variable
items_table: HASH_TABLE [WGI_VALUE, READABLE_STRING_GENERAL]
-- Table containing all the various variables -- Table containing all the various variables
-- Warning: this is computed each time, if you change the content of other containers -- Warning: this is computed each time, if you change the content of other containers
-- this won't update this Result's content, unless you query it again -- this won't update this Result's content, unless you query it again
local local
vars: HASH_TABLE [READABLE_STRING_GENERAL, READABLE_STRING_GENERAL] vars: ITERATION_CURSOR [WGI_VALUE]
do do
create Result.make (100) create Result.make (100)
vars := meta_variables vars := meta_variables
from from
vars.start -- vars.start
until until
vars.after vars.after
loop loop
Result.force (vars.item_for_iteration.as_string_32, vars.key_for_iteration) Result.force (vars.item, vars.item.name)
vars.forth vars.forth
end end
vars := query_parameters vars := query_parameters
from from
vars.start -- vars.start
until until
vars.after vars.after
loop loop
Result.force (vars.item_for_iteration.as_string_32, vars.key_for_iteration) Result.force (vars.item, vars.item.name)
vars.forth vars.forth
end end
vars := form_data_parameters vars := form_data_parameters
from from
vars.start -- vars.start
until until
vars.after vars.after
loop loop
Result.force (vars.item_for_iteration.as_string_32, vars.key_for_iteration) Result.force (vars.item, vars.item.name)
vars.forth vars.forth
end end
vars := cookies vars := cookies
from from
vars.start -- vars.start
until until
vars.after vars.after
loop loop
Result.force (vars.item_for_iteration.as_string_32, vars.key_for_iteration) Result.force (vars.item, vars.item.name)
vars.forth vars.forth
end end
end end
parameter (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 feature -- Access: global variable
items: ITERATION_CURSOR [WGI_VALUE]
do
Result := items_table.new_cursor
end
item (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
-- Variable named `a_name' from any of the variables container -- Variable named `a_name' from any of the variables container
-- and following a specific order -- and following a specific order
-- execution, environment, get, post, cookies -- execution, environment, get, post, cookies
local local
s: detachable READABLE_STRING_GENERAL v: detachable WGI_VALUE
do do
s := meta_variable (a_name) v := meta_variable (a_name)
if s = Void then if v = Void then
s := query_parameter (a_name) v := query_parameter (a_name)
if s = Void then if v = Void then
s := form_data_parameter (a_name) v := form_data_parameter (a_name)
if s = Void then if v = Void then
s := cookie (a_name) v := cookie (a_name)
end end
end end
end end
if s /= Void then -- if s /= Void then
Result := s.as_string_32 -- Result := s.as_string_32
-- end
end
string_item (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32
do
if attached {WGI_STRING_VALUE} item (a_name) as val then
Result := val.string
else
check is_string_value: False end
end end
end end
@@ -862,7 +914,7 @@ feature {NONE} -- Temporary File handling
feature {NONE} -- Implementation: Form analyzer feature {NONE} -- Implementation: Form analyzer
analyze_multipart_form (t: STRING; s: STRING; vars: like form_data_parameters) analyze_multipart_form (t: STRING; s: STRING; vars: like form_data_parameters_table)
-- Analyze multipart form content -- Analyze multipart form content
--| FIXME[2011-06-21]: integrate eMIME parser library --| FIXME[2011-06-21]: integrate eMIME parser library
require require
@@ -928,7 +980,7 @@ feature {NONE} -- Implementation: Form analyzer
end end
end end
analyze_multipart_form_input (s: STRING; vars_post: like form_data_parameters) analyze_multipart_form_input (s: STRING; vars_post: like form_data_parameters_table)
-- Analyze multipart entry -- Analyze multipart entry
require require
s_not_empty: s /= Void and then not s.is_empty s_not_empty: s /= Void and then not s.is_empty
@@ -1035,7 +1087,7 @@ feature {NONE} -- Implementation: Form analyzer
save_uploaded_file (l_content, l_up_file_info) save_uploaded_file (l_content, l_up_file_info)
uploaded_files.force (l_up_file_info, l_name) uploaded_files.force (l_up_file_info, l_name)
else else
vars_post.force (l_content, l_name) vars_post.force (new_string_value (l_name, l_content), l_name)
end end
else else
error_handler.add_custom_error (0, "unamed multipart entry", Void) error_handler.add_custom_error (0, "unamed multipart entry", Void)
@@ -1075,13 +1127,13 @@ feature {NONE} -- Internal value
end end
end end
internal_query_parameters: detachable like query_parameters internal_query_parameters_table: detachable like query_parameters_table
-- cached value for `query_parameters' -- cached value for `query_parameters'
internal_form_data_parameters: detachable like form_data_parameters internal_form_data_parameters_table: detachable like form_data_parameters_table
-- cached value for `form_fields' -- cached value for `form_fields'
internal_cookies: detachable like cookies internal_cookies_table: detachable like cookies_table
-- cached value for `cookies' -- cached value for `cookies'
feature {NONE} -- I/O: implementation feature {NONE} -- I/O: implementation
@@ -1138,7 +1190,12 @@ feature {NONE} -- Implementation
end end
end end
feature {NONE} -- Implementation: utilities feature {NONE} -- Implementation: utilities
new_string_value (a_name: READABLE_STRING_GENERAL; a_value: READABLE_STRING_32): WGI_STRING_VALUE
do
create Result.make (a_name, a_value)
end
empty_string: READABLE_STRING_32 empty_string: READABLE_STRING_32
-- Reusable empty string -- Reusable empty string

View File

@@ -20,7 +20,6 @@ feature {NONE} -- Initialization
router := a_router router := a_router
base_doc_url := a_base_doc_url base_doc_url := a_base_doc_url
description := "Technical documention for the API" description := "Technical documention for the API"
initialize
end end
feature {NONE} -- Access: Implementation feature {NONE} -- Access: Implementation
@@ -31,7 +30,9 @@ feature {NONE} -- Access: Implementation
feature -- Access feature -- Access
authentication_required: BOOLEAN = False authentication_required (req: WGI_REQUEST): BOOLEAN
do
end
feature -- Execution feature -- Execution
@@ -48,7 +49,10 @@ feature -- Execution
rep.headers.put_content_type_text_html rep.headers.put_content_type_text_html
create s.make_empty create s.make_empty
if attached ctx.path_parameter ("resource") as l_resource then if
attached {WGI_STRING_VALUE} ctx.path_parameter ("resource") as l_resource_value and then
attached l_resource_value.string as l_resource
then
from from
hdl_cursor := router.new_cursor hdl_cursor := router.new_cursor
until until
@@ -184,8 +188,8 @@ feature -- Execution
end end
s.append_string ("</strong></div>") s.append_string ("</strong></div>")
end end
s.append_string ("<div class=%"api-auth%">Authentication required: <strong>" + rq.authentication_required.out + "</strong></div>") s.append_string ("<div class=%"api-auth%">Authentication required: <strong>" + rq.authentication_required (req).out + "</strong></div>")
if attached {REST_REQUEST_URI_TEMPLATE_ROUTER [REST_REQUEST_HANDLER [REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT], REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT]} router as l_uri_template_router then if attached {REST_REQUEST_URI_TEMPLATE_ROUTER_I [REST_REQUEST_HANDLER [REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT], REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT]} router as l_uri_template_router then
create l_uri_tpl.make (a_resource) create l_uri_tpl.make (a_resource)
if attached l_uri_tpl.query_variable_names as l_query_variable_names and then not l_query_variable_names.is_empty then if attached l_uri_tpl.query_variable_names as l_query_variable_names and then not l_query_variable_names.is_empty then
s.append_string ("<div class=%"api-uri-template%">Query parameters: ") s.append_string ("<div class=%"api-uri-template%">Query parameters: ")

View File

@@ -1,165 +0,0 @@
note
description: "Summary description for {REST_REQUEST_HANDLER}."
author: ""
date: "$Date$"
revision: "$Revision$"
deferred class
REST_REQUEST_HANDLER [C -> REST_REQUEST_HANDLER_CONTEXT]
inherit
REQUEST_HANDLER [C]
redefine
execute
end
feature -- Access
authentication_required: BOOLEAN
-- Is authentication required
-- might depend on the request environment
-- or the associated resources
deferred
end
feature -- Execution
execute (a_hdl_context: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
-- Execute request handler
do
if authentication_required and then not a_hdl_context.authenticated then
execute_unauthorized (a_hdl_context, req, res)
else
Precursor (a_hdl_context, req, res)
end
end
execute_unauthorized (a_hdl_context: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
do
res.set_status_code ({HTTP_STATUS_CODE}.unauthorized)
res.write_header ({HTTP_STATUS_CODE}.unauthorized, <<["WWW-Authenticate", "Basic realm=%"Eiffel auth%""]>>)
res.write_string ("Unauthorized")
end
feature {NONE} -- Implementation
supported_formats: INTEGER
-- Support request format result such as json, xml, ...
feature {NONE} -- Status report
format_id_supported (a_id: INTEGER): BOOLEAN
do
Result := (supported_formats & a_id) = a_id
end
format_name_supported (n: STRING): BOOLEAN
-- Is format `n' supported?
do
Result := format_id_supported (format_constants.format_id (n))
end
format_constants: HTTP_FORMAT_CONSTANTS
once
create Result
end
feature -- Status report
supported_format_names: LIST [STRING]
-- Supported format names ...
do
create {LINKED_LIST [STRING]} Result.make
if format_json_supported then
Result.extend (format_constants.json_name)
end
if format_xml_supported then
Result.extend (format_constants.xml_name)
end
if format_text_supported then
Result.extend (format_constants.text_name)
end
if format_html_supported then
Result.extend (format_constants.html_name)
end
if format_rss_supported then
Result.extend (format_constants.rss_name)
end
if format_atom_supported then
Result.extend (format_constants.atom_name)
end
end
format_json_supported: BOOLEAN
do
Result := format_id_supported ({HTTP_FORMAT_CONSTANTS}.json)
end
format_xml_supported: BOOLEAN
do
Result := format_id_supported ({HTTP_FORMAT_CONSTANTS}.xml)
end
format_text_supported: BOOLEAN
do
Result := format_id_supported ({HTTP_FORMAT_CONSTANTS}.text)
end
format_html_supported: BOOLEAN
do
Result := format_id_supported ({HTTP_FORMAT_CONSTANTS}.html)
end
format_rss_supported: BOOLEAN
do
Result := format_id_supported ({HTTP_FORMAT_CONSTANTS}.rss)
end
format_atom_supported: BOOLEAN
do
Result := format_id_supported ({HTTP_FORMAT_CONSTANTS}.atom)
end
feature -- Element change: formats
reset_supported_formats
do
supported_formats := 0
end
enable_format_json
do
enable_format ({HTTP_FORMAT_CONSTANTS}.json)
end
enable_format_xml
do
enable_format ({HTTP_FORMAT_CONSTANTS}.xml)
end
enable_format_text
do
enable_format ({HTTP_FORMAT_CONSTANTS}.text)
end
enable_format_html
do
enable_format ({HTTP_FORMAT_CONSTANTS}.html)
end
enable_format (f: INTEGER)
do
supported_formats := supported_formats | f
end
note
copyright: "Copyright (c) 1984-2011, Eiffel Software and others"
license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)"
source: "[
Eiffel Software
5949 Hollister Ave., Goleta, CA 93117 USA
Telephone 805-685-1006, Fax 805-685-6869
Website http://www.eiffel.com
Customer support http://support.eiffel.com
]"
end

View File

@@ -5,10 +5,10 @@ note
revision: "$Revision$" revision: "$Revision$"
deferred class deferred class
DEFAULT_REST_APPLICATION REST_APPLICATION
inherit inherit
REST_APPLICATION [REST_REQUEST_HANDLER [REST_REQUEST_HANDLER_CONTEXT], REST_REQUEST_HANDLER_CONTEXT] REST_APPLICATION_I [REST_REQUEST_HANDLER [REST_REQUEST_HANDLER_CONTEXT], REST_REQUEST_HANDLER_CONTEXT]
note note
copyright: "Copyright (c) 1984-2011, Eiffel Software and others" copyright: "Copyright (c) 1984-2011, Eiffel Software and others"

View File

@@ -5,10 +5,10 @@ note
revision: "$Revision$" revision: "$Revision$"
deferred class deferred class
REST_APPLICATION [H -> REST_REQUEST_HANDLER [C], C -> REST_REQUEST_HANDLER_CONTEXT] REST_APPLICATION_I [H -> REST_REQUEST_HANDLER [C], C -> REST_REQUEST_HANDLER_CONTEXT]
inherit inherit
ROUTED_APPLICATION [H, C] ROUTED_APPLICATION_I [H, C]
redefine redefine
router router
end end

View File

@@ -22,26 +22,33 @@ create
feature -- status feature -- status
authentication_required: BOOLEAN authentication_required (req: WGI_REQUEST): BOOLEAN
do
Result := internal_authentication_required
end
feature -- Element change feature -- Element change
set_authentication_required (b: like authentication_required) set_authentication_required (b: like authentication_required)
do do
authentication_required := b internal_authentication_required := b
end end
feature {NONE} -- Implementation
internal_authentication_required: BOOLEAN
feature -- Execution feature -- Execution
execute (a_hdl_context: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER) execute (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
do do
Precursor {REST_REQUEST_HANDLER} (a_hdl_context, req, res) Precursor {REST_REQUEST_HANDLER} (ctx, req, res)
end end
-- execute_application (ctx: REST_REQUEST_HANDLER_CONTEXT; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER) execute_application (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
-- do do
-- action.call ([ctx, req, res]) check should_not_occur: False end
-- end end
;note ;note
copyright: "Copyright (c) 1984-2011, Eiffel Software and others" copyright: "Copyright (c) 1984-2011, Eiffel Software and others"

View File

@@ -1,54 +1,54 @@
note note
description: "Summary description for {REQUEST_HANDLER}." description: "Summary description for {REST_REQUEST_HANDLER}."
author: "" author: ""
date: "$Date$" date: "$Date$"
revision: "$Revision$" revision: "$Revision$"
deferred class deferred class
REQUEST_HANDLER [C -> REQUEST_HANDLER_CONTEXT] REST_REQUEST_HANDLER [C -> REST_REQUEST_HANDLER_CONTEXT]
inherit inherit
ANY REQUEST_HANDLER [C]
redefine
ROUTED_APPLICATION_HELPER execute
export
{NONE} all
end
feature {NONE} -- Initialization
initialize
-- Initialize various attributes
do
end end
feature -- Access feature -- Access
authentication_required (req: WGI_REQUEST): BOOLEAN
-- Is authentication required
-- might depend on the request environment
-- or the associated resources
deferred
end
description: detachable STRING description: detachable STRING
-- Optional descriptiong -- Optional descriptiong
feature -- Status report feature -- Element change
is_valid_context (req: WGI_REQUEST): BOOLEAN set_description (s: like description)
-- Is `req' valid context for current handler? -- Set `description' to `s'
do do
Result := request_method_name_supported (req.request_method) description := s
end end
feature -- Execution feature -- Execution
execute (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER) execute (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
-- Execute request handler -- Execute request handler
require
is_valid_context: is_valid_context (req)
local local
rescued: BOOLEAN rescued: BOOLEAN
do do
if not rescued then if not rescued then
if request_method_name_supported (req.request_method) then if request_method_name_supported (req.request_method) then
pre_execute (ctx, req, res) if authentication_required (req) and then not ctx.authenticated then
execute_application (ctx, req, res) execute_unauthorized (ctx, req, res)
post_execute (ctx, req, res) else
pre_execute (ctx, req, res)
execute_application (ctx, req, res)
post_execute (ctx, req, res)
end
else else
execute_request_method_not_allowed (req, res, supported_request_method_names) execute_request_method_not_allowed (req, res, supported_request_method_names)
end end
@@ -61,68 +61,137 @@ feature -- Execution
end end
execute_application (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER) execute_application (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
-- Execute request handler
deferred deferred
end end
pre_execute (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER) pre_execute (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
-- Operation processed before `execute'
do do
--| To be redefined if needed
end end
post_execute (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER) post_execute (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
-- Operation processed after `execute'
do do
--| To be redefined if needed
end end
rescue_execute (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER) rescue_execute (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
-- Operation processed after a rescue
do do
--| To be redefined if needed
post_execute (ctx, req, res) post_execute (ctx, req, res)
end end
feature -- Execution: report execute_unauthorized (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
url (req: WGI_REQUEST; a_base: detachable READABLE_STRING_8; args: detachable STRING; abs: BOOLEAN): STRING
-- Associated url based on `a_base' and `args'
-- if `abs' then return absolute url
local
s: detachable STRING
l_base: STRING
do do
if a_base /= Void then res.set_status_code ({HTTP_STATUS_CODE}.unauthorized)
l_base := a_base res.write_header ({HTTP_STATUS_CODE}.unauthorized, Void)
else res.write_string ("Unauthorized")
l_base := req.request_uri end
end feature {NONE} -- Implementation
s := args
if s /= Void and then s.count > 0 then supported_formats: INTEGER
if s[1] /= '/' then -- Support request format result such as json, xml, ...
s := l_base + "/" + s
else feature {NONE} -- Status report
s := l_base + s
end format_id_supported (a_id: INTEGER): BOOLEAN
else do
s := l_base Result := (supported_formats & a_id) = a_id
end
if abs then
Result := req.absolute_script_url (s)
else
Result := req.script_url (s)
end
ensure
result_attached: Result /= Void
end end
feature -- Element change format_name_supported (n: STRING): BOOLEAN
-- Is format `n' supported?
set_description (s: like description)
-- Set `description' to `s'
do do
description := s Result := format_id_supported (format_constants.format_id (n))
end
format_constants: HTTP_FORMAT_CONSTANTS
once
create Result
end
feature -- Status report
supported_format_names: LIST [STRING]
-- Supported format names ...
do
create {LINKED_LIST [STRING]} Result.make
if format_json_supported then
Result.extend (format_constants.json_name)
end
if format_xml_supported then
Result.extend (format_constants.xml_name)
end
if format_text_supported then
Result.extend (format_constants.text_name)
end
if format_html_supported then
Result.extend (format_constants.html_name)
end
if format_rss_supported then
Result.extend (format_constants.rss_name)
end
if format_atom_supported then
Result.extend (format_constants.atom_name)
end
end
format_json_supported: BOOLEAN
do
Result := format_id_supported ({HTTP_FORMAT_CONSTANTS}.json)
end
format_xml_supported: BOOLEAN
do
Result := format_id_supported ({HTTP_FORMAT_CONSTANTS}.xml)
end
format_text_supported: BOOLEAN
do
Result := format_id_supported ({HTTP_FORMAT_CONSTANTS}.text)
end
format_html_supported: BOOLEAN
do
Result := format_id_supported ({HTTP_FORMAT_CONSTANTS}.html)
end
format_rss_supported: BOOLEAN
do
Result := format_id_supported ({HTTP_FORMAT_CONSTANTS}.rss)
end
format_atom_supported: BOOLEAN
do
Result := format_id_supported ({HTTP_FORMAT_CONSTANTS}.atom)
end
feature -- Element change: formats
reset_supported_formats
do
supported_formats := 0
end
enable_format_json
do
enable_format ({HTTP_FORMAT_CONSTANTS}.json)
end
enable_format_xml
do
enable_format ({HTTP_FORMAT_CONSTANTS}.xml)
end
enable_format_text
do
enable_format ({HTTP_FORMAT_CONSTANTS}.text)
end
enable_format_html
do
enable_format ({HTTP_FORMAT_CONSTANTS}.html)
end
enable_format (f: INTEGER)
do
supported_formats := supported_formats | f
end end
feature {NONE} -- Implementation feature {NONE} -- Implementation
@@ -233,8 +302,10 @@ feature -- Element change: request methods
supported_request_methods := supported_request_methods | m supported_request_methods := supported_request_methods | m
end end
note note
copyright: "2011-2011, Eiffel Software and others" copyright: "Copyright (c) 1984-2011, Eiffel Software and others"
license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)" license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)"
source: "[ source: "[
Eiffel Software Eiffel Software

View File

@@ -5,7 +5,7 @@ note
revision: "$Revision$" revision: "$Revision$"
deferred class deferred class
DEFAULT_REST_REQUEST_URI_HANDLER REST_REQUEST_URI_HANDLER
inherit inherit
REST_REQUEST_HANDLER [REST_REQUEST_URI_HANDLER_CONTEXT] REST_REQUEST_HANDLER [REST_REQUEST_URI_HANDLER_CONTEXT]

View File

@@ -16,7 +16,7 @@ create
make make
note note
copyright: "2011-2011, Eiffel Software and others" copyright: "Copyright (c) 1984-2011, Eiffel Software and others"
license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)" license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)"
source: "[ source: "[
Eiffel Software Eiffel Software

View File

@@ -5,10 +5,10 @@ note
revision: "$Revision$" revision: "$Revision$"
class class
DEFAULT_REST_REQUEST_URI_ROUTER REST_REQUEST_URI_ROUTER
inherit inherit
REST_REQUEST_URI_ROUTER [REST_REQUEST_HANDLER [REST_REQUEST_URI_HANDLER_CONTEXT], REST_REQUEST_URI_HANDLER_CONTEXT] REST_REQUEST_URI_ROUTER_I [REST_REQUEST_HANDLER [REST_REQUEST_URI_HANDLER_CONTEXT], REST_REQUEST_URI_HANDLER_CONTEXT]
redefine redefine
map_agent_with_request_methods map_agent_with_request_methods
end end

View File

@@ -5,10 +5,10 @@ note
revision: "$Revision$" revision: "$Revision$"
class class
REST_REQUEST_URI_ROUTER [H -> REST_REQUEST_HANDLER [C], C -> REST_REQUEST_URI_HANDLER_CONTEXT create make end] REST_REQUEST_URI_ROUTER_I [H -> REST_REQUEST_HANDLER [C], C -> REST_REQUEST_URI_HANDLER_CONTEXT create make end]
inherit inherit
REQUEST_URI_ROUTER [H, C] REQUEST_URI_ROUTER_I [H, C]
REST_REQUEST_ROUTER [H, C] REST_REQUEST_ROUTER [H, C]

View File

@@ -0,0 +1,33 @@
note
description: "Summary description for {DEFAULT_REST_REQUEST_URI_ROUTING_HANDLER}."
author: ""
date: "$Date$"
revision: "$Revision$"
class
REST_REQUEST_URI_ROUTING_HANDLER
inherit
REST_REQUEST_URI_ROUTING_HANDLER_I [REST_REQUEST_HANDLER [REST_REQUEST_URI_HANDLER_CONTEXT], REST_REQUEST_URI_HANDLER_CONTEXT]
redefine
router
end
create
make
feature {NONE} -- Routing
router: REST_REQUEST_URI_ROUTER
;note
copyright: "Copyright (c) 1984-2011, Eiffel Software and others"
license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)"
source: "[
Eiffel Software
5949 Hollister Ave., Goleta, CA 93117 USA
Telephone 805-685-1006, Fax 805-685-6869
Website http://www.eiffel.com
Customer support http://support.eiffel.com
]"
end

View File

@@ -5,11 +5,11 @@ note
revision: "$Revision$" revision: "$Revision$"
class class
REST_REQUEST_URI_ROUTING_HANDLER [H -> REST_REQUEST_HANDLER [C], REST_REQUEST_URI_ROUTING_HANDLER_I [H -> REST_REQUEST_HANDLER [C],
C -> REST_REQUEST_URI_HANDLER_CONTEXT create make end] C -> REST_REQUEST_URI_HANDLER_CONTEXT create make end]
inherit inherit
REQUEST_URI_ROUTING_HANDLER [H, C] REQUEST_URI_ROUTING_HANDLER_I [H, C]
redefine redefine
router, router,
execute execute
@@ -22,21 +22,27 @@ inherit
create create
make make
feature -- Status report feature -- Status report
authentication_required: BOOLEAN authentication_required: BOOLEAN
feature -- Execution feature -- Execution
execute (a_hdl_context: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER) execute (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
do do
Precursor {REST_REQUEST_HANDLER} (a_hdl_context, req, res) Precursor {REST_REQUEST_HANDLER} (ctx, req, res)
end end
execute_application (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
do
check should_not_occur: False end
end
feature {NONE} -- Routing feature {NONE} -- Routing
router: REST_REQUEST_URI_ROUTER [H, C] router: REST_REQUEST_URI_ROUTER_I [H, C]
;note ;note
copyright: "Copyright (c) 1984-2011, Eiffel Software and others" copyright: "Copyright (c) 1984-2011, Eiffel Software and others"

View File

@@ -5,17 +5,17 @@ note
revision: "$Revision$" revision: "$Revision$"
deferred class deferred class
DEFAULT_REST_URI_APPLICATION REST_URI_APPLICATION
inherit inherit
REST_APPLICATION [REST_REQUEST_HANDLER [REST_REQUEST_URI_HANDLER_CONTEXT], REST_REQUEST_URI_HANDLER_CONTEXT] REST_APPLICATION_I [REST_REQUEST_HANDLER [REST_REQUEST_URI_HANDLER_CONTEXT], REST_REQUEST_URI_HANDLER_CONTEXT]
redefine redefine
router router
end end
feature -- Router feature -- Router
router: DEFAULT_REST_REQUEST_URI_ROUTER router: REST_REQUEST_URI_ROUTER
;note ;note
copyright: "Copyright (c) 1984-2011, Eiffel Software and others" copyright: "Copyright (c) 1984-2011, Eiffel Software and others"

View File

@@ -5,7 +5,7 @@ note
revision: "$Revision$" revision: "$Revision$"
deferred class deferred class
DEFAULT_REST_REQUEST_URI_TEMPLATE_HANDLER REST_REQUEST_URI_TEMPLATE_HANDLER
inherit inherit
REST_REQUEST_HANDLER [REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT] REST_REQUEST_HANDLER [REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT]

View File

@@ -16,7 +16,7 @@ create
make make
note note
copyright: "2011-2011, Eiffel Software and others" copyright: "Copyright (c) 1984-2011, Eiffel Software and others"
license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)" license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)"
source: "[ source: "[
Eiffel Software Eiffel Software

View File

@@ -5,10 +5,10 @@ note
revision: "$Revision$" revision: "$Revision$"
class class
DEFAULT_REST_REQUEST_URI_TEMPLATE_ROUTER REST_REQUEST_URI_TEMPLATE_ROUTER
inherit inherit
REST_REQUEST_URI_TEMPLATE_ROUTER [REST_REQUEST_HANDLER [REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT], REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT] REST_REQUEST_URI_TEMPLATE_ROUTER_I [REST_REQUEST_HANDLER [REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT], REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT]
redefine redefine
map_agent_with_request_methods map_agent_with_request_methods
end end

View File

@@ -5,10 +5,10 @@ note
revision: "$Revision$" revision: "$Revision$"
class class
REST_REQUEST_URI_TEMPLATE_ROUTER [H -> REST_REQUEST_HANDLER [C], C -> REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT create make end] REST_REQUEST_URI_TEMPLATE_ROUTER_I [H -> REST_REQUEST_HANDLER [C], C -> REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT create make end]
inherit inherit
REQUEST_URI_TEMPLATE_ROUTER [H, C] REQUEST_URI_TEMPLATE_ROUTER_I [H, C]
REST_REQUEST_ROUTER [H, C] REST_REQUEST_ROUTER [H, C]

View File

@@ -5,10 +5,10 @@ note
revision: "$Revision$" revision: "$Revision$"
class class
DEFAULT_REST_REQUEST_URI_TEMPLATE_ROUTING_HANDLER REST_REQUEST_URI_TEMPLATE_ROUTING_HANDLER
inherit inherit
REST_REQUEST_URI_TEMPLATE_ROUTING_HANDLER [REST_REQUEST_HANDLER [REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT], REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT] REST_REQUEST_URI_TEMPLATE_ROUTING_HANDLER_I [REST_REQUEST_HANDLER [REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT], REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT]
redefine redefine
router router
end end
@@ -18,7 +18,7 @@ create
feature {NONE} -- Routing feature {NONE} -- Routing
router: DEFAULT_REST_REQUEST_URI_TEMPLATE_ROUTER router: REST_REQUEST_URI_TEMPLATE_ROUTER
;note ;note
copyright: "Copyright (c) 1984-2011, Eiffel Software and others" copyright: "Copyright (c) 1984-2011, Eiffel Software and others"

View File

@@ -5,11 +5,11 @@ note
revision: "$Revision$" revision: "$Revision$"
class class
REST_REQUEST_URI_TEMPLATE_ROUTING_HANDLER [H -> REST_REQUEST_HANDLER [C], REST_REQUEST_URI_TEMPLATE_ROUTING_HANDLER_I [H -> REST_REQUEST_HANDLER [C],
C -> REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT create make end] C -> REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT create make end]
inherit inherit
REQUEST_URI_TEMPLATE_ROUTING_HANDLER [H, C] REQUEST_URI_TEMPLATE_ROUTING_HANDLER_I [H, C]
redefine redefine
router, router,
execute execute
@@ -22,21 +22,33 @@ inherit
create create
make make
feature -- Status report feature -- Status report
authentication_required: BOOLEAN authentication_required (req: WGI_REQUEST): BOOLEAN
do
Result := internal_authentication_required
end
feature {NONE} -- Implementation
internal_authentication_required: BOOLEAN
feature -- Execution feature -- Execution
execute (a_hdl_context: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER) execute (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
do do
Precursor {REST_REQUEST_HANDLER} (a_hdl_context, req, res) Precursor {REST_REQUEST_HANDLER} (ctx, req, res)
end
execute_application (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
do
check should_not_occur: False end
end end
feature {NONE} -- Routing feature {NONE} -- Routing
router: REST_REQUEST_URI_TEMPLATE_ROUTER [H, C] router: REST_REQUEST_URI_TEMPLATE_ROUTER_I [H, C]
;note ;note
copyright: "Copyright (c) 1984-2011, Eiffel Software and others" copyright: "Copyright (c) 1984-2011, Eiffel Software and others"

View File

@@ -5,17 +5,17 @@ note
revision: "$Revision$" revision: "$Revision$"
deferred class deferred class
DEFAULT_REST_URI_TEMPLATE_APPLICATION REST_URI_TEMPLATE_APPLICATION
inherit inherit
REST_APPLICATION [REST_REQUEST_HANDLER [REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT], REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT] REST_APPLICATION_I [REST_REQUEST_HANDLER [REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT], REST_REQUEST_URI_TEMPLATE_HANDLER_CONTEXT]
redefine redefine
router router
end end
feature -- Router feature -- Router
router: DEFAULT_REST_REQUEST_URI_TEMPLATE_ROUTER router: REST_REQUEST_URI_TEMPLATE_ROUTER
;note ;note
copyright: "Copyright (c) 1984-2011, Eiffel Software and others" copyright: "Copyright (c) 1984-2011, Eiffel Software and others"

View File

@@ -2,7 +2,7 @@ Options Indexes FollowSymLinks ExecCGI
<IfModule mod_fcgid.c> <IfModule mod_fcgid.c>
AddHandler fcgid-script .eapp AddHandler fcgid-script .eapp
FcgidWrapper c:/_dev/Dev-Process/web-library/library/server/rest/tests/htdocs/../EIFGENs/rest_sample_cgi/W_code/sample.exe .eapp FcgidWrapper c:/_dev/Dev-Process/web-framework/library/server/request/rest/tests/htdocs/../EIFGENs/rest_sample_cgi/W_code/sample.exe .eapp
</IfModule> </IfModule>

View File

@@ -35,7 +35,10 @@ feature {NONE} -- Initialization
feature -- Access feature -- Access
authentication_required: BOOLEAN = True authentication_required (req: WGI_REQUEST): BOOLEAN
do
Result := True
end
feature -- Execution feature -- Execution

View File

@@ -32,7 +32,9 @@ feature {NONE} -- Initialization
feature -- Access feature -- Access
authentication_required: BOOLEAN = False authentication_required (req: WGI_REQUEST): BOOLEAN
do
end
feature -- Execution feature -- Execution
@@ -47,8 +49,8 @@ feature -- Execution
create s.make_empty create s.make_empty
s.append_string ("test") s.append_string ("test")
if attached req.meta_variable ("REQUEST_COUNT") as l_request_count then if attached req.meta_variable ("REQUEST_COUNT") as l_request_count_val then
s.append_string ("(request_count="+ l_request_count +")%N") s.append_string ("(request_count="+ l_request_count_val.as_string +")%N")
end end
-- ctx.request_format_id ("format", Void) -- ctx.request_format_id ("format", Void)
@@ -57,13 +59,13 @@ feature -- Execution
s.append_string (" format=" + l_format + "%N") s.append_string (" format=" + l_format + "%N")
end end
if attached ctx.parameter ("op") as l_op then if attached ctx.string_parameter ("op") as l_op then
s.append_string (" op=" + l_op) s.append_string (" op=" + l_op)
if l_op.same_string ("crash") then if l_op.same_string ("crash") then
(create {DEVELOPER_EXCEPTION}).raise (create {DEVELOPER_EXCEPTION}).raise
elseif l_op.starts_with ("env") then elseif l_op.starts_with ("env") then
s.append_string ("%N%NAll variables:") s.append_string ("%N%NAll variables:")
s.append (string_hash_table_string_string (req.parameters.new_cursor, False)) s.append (wgi_value_iteration_to_string (req.parameters, False))
s.append_string ("<br/>script_url(%"" + req.path_info + "%")=" + ctx.script_url (req.path_info) + "%N") s.append_string ("<br/>script_url(%"" + req.path_info + "%")=" + ctx.script_url (req.path_info) + "%N")
-- if attached ctx.http_authorization_login_password as t then -- if attached ctx.http_authorization_login_password as t then
-- s.append_string ("Check login=" + t.login + "<br/>%N") -- s.append_string ("Check login=" + t.login + "<br/>%N")

View File

@@ -8,7 +8,7 @@ deferred class
APP_APPLICATION APP_APPLICATION
inherit inherit
REST_APPLICATION [APP_REQUEST_HANDLER, APP_REQUEST_HANDLER_CONTEXT] REST_APPLICATION_I [APP_REQUEST_HANDLER, APP_REQUEST_HANDLER_CONTEXT]
redefine redefine
router router
end end

View File

@@ -11,21 +11,27 @@ inherit
APP_REQUEST_HELPER APP_REQUEST_HELPER
feature {NONE} -- Initialization
initialize
-- Initialize various attributes
do
end
feature {NONE} -- Implementation feature {NONE} -- Implementation
string_hash_table_string_string (ht: HASH_TABLE_ITERATION_CURSOR [READABLE_STRING_GENERAL, READABLE_STRING_GENERAL]; using_pre: BOOLEAN): STRING_8 wgi_value_iteration_to_string (cur: ITERATION_CURSOR [WGI_VALUE]; using_pre: BOOLEAN): STRING_8
do do
create Result.make (100) create Result.make (100)
if using_pre then if using_pre then
Result.append ("<pre>") Result.append ("<pre>")
end end
from from
ht.start
until until
ht.after cur.after
loop loop
Result.append_string (ht.key.as_string_8 + " = " + ht.item.as_string_8 + "%N") Result.append_string (cur.item.name.as_string_8 + " = " + cur.item.as_string.as_string_8 + "%N")
ht.forth cur.forth
end end
if using_pre then if using_pre then
Result.append ("</pre>") Result.append ("</pre>")

View File

@@ -8,7 +8,7 @@ class
APP_REQUEST_ROUTER APP_REQUEST_ROUTER
inherit inherit
REST_REQUEST_URI_TEMPLATE_ROUTER [APP_REQUEST_HANDLER, APP_REQUEST_HANDLER_CONTEXT] REST_REQUEST_URI_TEMPLATE_ROUTER_I [APP_REQUEST_HANDLER, APP_REQUEST_HANDLER_CONTEXT]
create create
make make

View File

@@ -15,7 +15,7 @@ inherit
post_execute post_execute
end end
REST_REQUEST_URI_TEMPLATE_ROUTING_HANDLER [APP_REQUEST_HANDLER, APP_REQUEST_HANDLER_CONTEXT] REST_REQUEST_URI_TEMPLATE_ROUTING_HANDLER_I [APP_REQUEST_HANDLER, APP_REQUEST_HANDLER_CONTEXT]
redefine redefine
router router
end end

View File

@@ -5,10 +5,10 @@ note
revision: "$Revision$" revision: "$Revision$"
deferred class deferred class
DEFAULT_ROUTED_APPLICATION ROUTED_APPLICATION
inherit inherit
ROUTED_APPLICATION [REQUEST_HANDLER [REQUEST_HANDLER_CONTEXT], REQUEST_HANDLER_CONTEXT] ROUTED_APPLICATION_I [REQUEST_HANDLER [REQUEST_HANDLER_CONTEXT], REQUEST_HANDLER_CONTEXT]
note note
copyright: "2011-2011, Eiffel Software and others" copyright: "2011-2011, Eiffel Software and others"

View File

@@ -18,7 +18,6 @@ feature -- Initialization
make (act: like action) make (act: like action)
do do
action := act action := act
initialize
end end
feature -- Access feature -- Access
@@ -27,7 +26,7 @@ feature -- Access
feature -- Execution feature -- Execution
execute_application (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER) execute (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
do do
action.call ([ctx, req, res]) action.call ([ctx, req, res])
end end

View File

@@ -0,0 +1,78 @@
note
description: "Summary description for {REQUEST_HANDLER}."
author: ""
date: "$Date$"
revision: "$Revision$"
deferred class
REQUEST_HANDLER [C -> REQUEST_HANDLER_CONTEXT]
inherit
ANY
ROUTED_APPLICATION_HELPER
export
{NONE} all
end
feature -- Status report
is_valid_context (req: WGI_REQUEST): BOOLEAN
-- Is `req' valid context for current handler?
do
Result := True
end
feature -- Execution
execute (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
-- Execute request handler
require
is_valid_context: is_valid_context (req)
deferred
end
feature -- Execution: report
url (req: WGI_REQUEST; a_base: detachable READABLE_STRING_8; args: detachable STRING; abs: BOOLEAN): STRING
-- Associated url based on `a_base' and `args'
-- if `abs' then return absolute url
local
s: detachable STRING
l_base: STRING
do
if a_base /= Void then
l_base := a_base
else
l_base := req.request_uri
end
s := args
if s /= Void and then s.count > 0 then
if s[1] /= '/' then
s := l_base + "/" + s
else
s := l_base + s
end
else
s := l_base
end
if abs then
Result := req.absolute_script_url (s)
else
Result := req.script_url (s)
end
ensure
result_attached: Result /= Void
end
note
copyright: "2011-2011, Eiffel Software and others"
license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)"
source: "[
Eiffel Software
5949 Hollister Ave., Goleta, CA 93117 USA
Telephone 805-685-1006, Fax 805-685-6869
Website http://www.eiffel.com
Customer support http://support.eiffel.com
]"
end

View File

@@ -35,7 +35,7 @@ feature -- Query
request_format (a_format_variable_name: detachable READABLE_STRING_GENERAL; content_type_supported: detachable ARRAY [READABLE_STRING_8]): detachable READABLE_STRING_8 request_format (a_format_variable_name: detachable READABLE_STRING_GENERAL; content_type_supported: detachable ARRAY [READABLE_STRING_8]): detachable READABLE_STRING_8
-- Format id for the request based on {HTTP_FORMAT_CONSTANTS} -- Format id for the request based on {HTTP_FORMAT_CONSTANTS}
do do
if a_format_variable_name /= Void and then attached parameter (a_format_variable_name) as ctx_format then if a_format_variable_name /= Void and then attached string_parameter (a_format_variable_name) as ctx_format then
Result := ctx_format.as_string_8 Result := ctx_format.as_string_8
else else
Result := content_type_to_request_format (request_content_type (content_type_supported)) Result := content_type_to_request_format (request_content_type (content_type_supported))
@@ -107,27 +107,51 @@ feature -- Query
feature -- Query feature -- Query
path_parameter (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 path_parameter (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
-- Parameter value for path variable `a_name' -- Parameter value for path variable `a_name'
deferred deferred
end end
query_parameter (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 query_parameter (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
-- Parameter value for query variable `a_name' -- Parameter value for query variable `a_name'
--| i.e after the ? character --| i.e after the ? character
deferred deferred
end end
parameter (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 parameter (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
-- Any parameter value for variable `a_name' -- Any parameter value for variable `a_name'
-- URI template parameter and query parameters -- URI template parameter and query parameters
do do
Result := query_parameter (a_name) Result := query_parameter (a_name)
if Result = Void then if Result = Void then
Result := path_parameter (a_name) Result := path_parameter (a_name)
end end
end end
feature -- String query
string_from (a_value: detachable WGI_VALUE): detachable READABLE_STRING_32
do
if attached {WGI_STRING_VALUE} a_value as val then
Result := val.string
end
end
string_path_parameter (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32
do
Result := string_from (path_parameter (a_name))
end
string_query_parameter (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32
do
Result := string_from (query_parameter (a_name))
end
string_parameter (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32
do
Result := string_from (parameter (a_name))
end
;note ;note
copyright: "2011-2011, Eiffel Software and others" copyright: "2011-2011, Eiffel Software and others"
license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)" license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)"

View File

@@ -13,7 +13,7 @@ inherit
feature -- Execution feature -- Execution
execute_application (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER) execute (ctx: C; req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
-- Execute request handler -- Execute request handler
local local
hdl: detachable H hdl: detachable H

View File

@@ -5,7 +5,7 @@ note
revision: "$Revision$" revision: "$Revision$"
deferred class deferred class
ROUTED_APPLICATION [H -> REQUEST_HANDLER [C], C -> REQUEST_HANDLER_CONTEXT] ROUTED_APPLICATION_I [H -> REQUEST_HANDLER [C], C -> REQUEST_HANDLER_CONTEXT]
feature -- Setup feature -- Setup
@@ -38,10 +38,15 @@ feature -- Execution
execute (req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER) execute (req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
local local
l_handled: BOOLEAN l_handled: BOOLEAN
rescued: BOOLEAN
do do
l_handled := router.dispatch (req, res) if not rescued then
if not l_handled then l_handled := router.dispatch (req, res)
execute_default (req, res) if not l_handled then
execute_default (req, res)
end
else
execute_rescue (req, res)
end end
end end
@@ -49,6 +54,14 @@ feature -- Execution
deferred deferred
end end
execute_rescue (req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
do
if not res.header_committed then
res.write_header ({HTTP_STATUS_CODE}.internal_server_error, Void)
end
res.flush
end
note note
copyright: "2011-2011, Eiffel Software and others" copyright: "2011-2011, Eiffel Software and others"
license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)" license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)"

View File

@@ -5,10 +5,10 @@ note
revision: "$Revision$" revision: "$Revision$"
class class
DEFAULT_REQUEST_URI_ROUTER REQUEST_URI_ROUTER
inherit inherit
REQUEST_URI_ROUTER [REQUEST_HANDLER [REQUEST_URI_HANDLER_CONTEXT], REQUEST_URI_HANDLER_CONTEXT] REQUEST_URI_ROUTER_I [REQUEST_HANDLER [REQUEST_URI_HANDLER_CONTEXT], REQUEST_URI_HANDLER_CONTEXT]
redefine redefine
map_agent_with_request_methods map_agent_with_request_methods
end end

View File

@@ -0,0 +1,33 @@
note
description: "Summary description for {DEFAULT_REQUEST_URI_ROUTING_HANDLER}."
author: ""
date: "$Date$"
revision: "$Revision$"
class
REQUEST_URI_ROUTING_HANDLER
inherit
REQUEST_URI_ROUTING_HANDLER_I [REQUEST_HANDLER [REQUEST_URI_HANDLER_CONTEXT], REQUEST_URI_HANDLER_CONTEXT]
redefine
router
end
create
make
feature {NONE} -- Routing
router: REQUEST_URI_ROUTER
;note
copyright: "2011-2011, Eiffel Software and others"
license: "Eiffel Forum License v2 (see http://www.eiffel.com/licensing/forum.txt)"
source: "[
Eiffel Software
5949 Hollister Ave., Goleta, CA 93117 USA
Telephone 805-685-1006, Fax 805-685-6869
Website http://www.eiffel.com
Customer support http://support.eiffel.com
]"
end

View File

@@ -5,17 +5,17 @@ note
revision: "$Revision$" revision: "$Revision$"
deferred class deferred class
DEFAULT_URI_ROUTED_APPLICATION URI_ROUTED_APPLICATION
inherit inherit
ROUTED_APPLICATION [REQUEST_HANDLER [REQUEST_URI_HANDLER_CONTEXT], REQUEST_URI_HANDLER_CONTEXT] ROUTED_APPLICATION_I [REQUEST_HANDLER [REQUEST_URI_HANDLER_CONTEXT], REQUEST_URI_HANDLER_CONTEXT]
redefine redefine
router router
end end
feature -- Router feature -- Router
router: DEFAULT_REQUEST_URI_ROUTER router: REQUEST_URI_ROUTER
;note ;note
copyright: "2011-2011, Eiffel Software and others" copyright: "2011-2011, Eiffel Software and others"

View File

@@ -23,13 +23,13 @@ feature {NONE} -- Initialization
feature -- Query feature -- Query
path_parameter (a_name: READABLE_STRING_GENERAL): detachable STRING_32 path_parameter (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
do do
end end
query_parameter (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 query_parameter (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
do do
Result := request.parameter (a_name) Result := request.query_parameter (a_name)
end end
note note

View File

@@ -5,7 +5,7 @@ note
revision: "$Revision$" revision: "$Revision$"
class class
REQUEST_URI_ROUTER [H -> REQUEST_HANDLER [C], C -> REQUEST_URI_HANDLER_CONTEXT create make end] REQUEST_URI_ROUTER_I [H -> REQUEST_HANDLER [C], C -> REQUEST_URI_HANDLER_CONTEXT create make end]
inherit inherit
REQUEST_ROUTER [H, C] REQUEST_ROUTER [H, C]

View File

@@ -5,7 +5,7 @@ note
revision: "$Revision$" revision: "$Revision$"
class class
REQUEST_URI_ROUTING_HANDLER [H -> REQUEST_HANDLER [C], REQUEST_URI_ROUTING_HANDLER_I [H -> REQUEST_HANDLER [C],
C -> REQUEST_URI_HANDLER_CONTEXT create make end] C -> REQUEST_URI_HANDLER_CONTEXT create make end]
inherit inherit
@@ -23,7 +23,7 @@ feature {NONE} -- Initialization
feature {NONE} -- Routing feature {NONE} -- Routing
router: REQUEST_URI_ROUTER [H, C] router: REQUEST_URI_ROUTER_I [H, C]
;note ;note
copyright: "2011-2011, Eiffel Software and others" copyright: "2011-2011, Eiffel Software and others"

View File

@@ -5,10 +5,10 @@ note
revision: "$Revision$" revision: "$Revision$"
class class
DEFAULT_REQUEST_URI_TEMPLATE_ROUTER REQUEST_URI_TEMPLATE_ROUTER
inherit inherit
REQUEST_URI_TEMPLATE_ROUTER [REQUEST_HANDLER [REQUEST_URI_TEMPLATE_HANDLER_CONTEXT], REQUEST_URI_TEMPLATE_HANDLER_CONTEXT] REQUEST_URI_TEMPLATE_ROUTER_I [REQUEST_HANDLER [REQUEST_URI_TEMPLATE_HANDLER_CONTEXT], REQUEST_URI_TEMPLATE_HANDLER_CONTEXT]
redefine redefine
map_agent_with_request_methods map_agent_with_request_methods
end end

View File

@@ -5,10 +5,10 @@ note
revision: "$Revision$" revision: "$Revision$"
class class
DEFAULT_REQUEST_URI_TEMPLATE_ROUTING_HANDLER REQUEST_URI_TEMPLATE_ROUTING_HANDLER
inherit inherit
REQUEST_URI_TEMPLATE_ROUTING_HANDLER [REQUEST_HANDLER [REQUEST_URI_TEMPLATE_HANDLER_CONTEXT], REQUEST_URI_TEMPLATE_HANDLER_CONTEXT] REQUEST_URI_TEMPLATE_ROUTING_HANDLER_I [REQUEST_HANDLER [REQUEST_URI_TEMPLATE_HANDLER_CONTEXT], REQUEST_URI_TEMPLATE_HANDLER_CONTEXT]
redefine redefine
router router
end end
@@ -18,7 +18,7 @@ create
feature {NONE} -- Routing feature {NONE} -- Routing
router: DEFAULT_REQUEST_URI_TEMPLATE_ROUTER router: REQUEST_URI_TEMPLATE_ROUTER
;note ;note
copyright: "2011-2011, Eiffel Software and others" copyright: "2011-2011, Eiffel Software and others"

View File

@@ -5,17 +5,17 @@ note
revision: "$Revision$" revision: "$Revision$"
deferred class deferred class
DEFAULT_URI_TEMPLATE_ROUTED_APPLICATION URI_TEMPLATE_ROUTED_APPLICATION
inherit inherit
ROUTED_APPLICATION [REQUEST_HANDLER [REQUEST_URI_TEMPLATE_HANDLER_CONTEXT], REQUEST_URI_TEMPLATE_HANDLER_CONTEXT] ROUTED_APPLICATION_I [REQUEST_HANDLER [REQUEST_URI_TEMPLATE_HANDLER_CONTEXT], REQUEST_URI_TEMPLATE_HANDLER_CONTEXT]
redefine redefine
router router
end end
feature -- Router feature -- Router
router: DEFAULT_REQUEST_URI_TEMPLATE_ROUTER router: REQUEST_URI_TEMPLATE_ROUTER
;note ;note
copyright: "2011-2011, Eiffel Software and others" copyright: "2011-2011, Eiffel Software and others"

View File

@@ -31,16 +31,19 @@ feature -- Access
feature -- Query feature -- Query
path_parameter (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 path_parameter (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
do do
Result := uri_template_match.url_decoded_path_variable (a_name) if attached uri_template_match.url_decoded_path_variable (a_name) as s then
create {WGI_STRING_VALUE} Result.make (a_name, s)
end
end end
query_parameter (a_name: READABLE_STRING_GENERAL): detachable READABLE_STRING_32 query_parameter (a_name: READABLE_STRING_GENERAL): detachable WGI_VALUE
do do
Result := uri_template_match.url_decoded_query_variable (a_name) if attached uri_template_match.url_decoded_query_variable (a_name) as s then
if Result = Void then create {WGI_STRING_VALUE} Result.make (a_name, s)
Result := request.parameter (a_name) else
Result := request.query_parameter (a_name)
end end
end end

View File

@@ -5,7 +5,7 @@ note
revision: "$Revision$" revision: "$Revision$"
class class
REQUEST_URI_TEMPLATE_ROUTER [H -> REQUEST_HANDLER [C], C -> REQUEST_URI_TEMPLATE_HANDLER_CONTEXT create make end] REQUEST_URI_TEMPLATE_ROUTER_I [H -> REQUEST_HANDLER [C], C -> REQUEST_URI_TEMPLATE_HANDLER_CONTEXT create make end]
inherit inherit
REQUEST_ROUTER [H, C] REQUEST_ROUTER [H, C]

View File

@@ -5,7 +5,7 @@ note
revision: "$Revision$" revision: "$Revision$"
class class
REQUEST_URI_TEMPLATE_ROUTING_HANDLER [H -> REQUEST_HANDLER [C], REQUEST_URI_TEMPLATE_ROUTING_HANDLER_I [H -> REQUEST_HANDLER [C],
C -> REQUEST_URI_TEMPLATE_HANDLER_CONTEXT create make end] C -> REQUEST_URI_TEMPLATE_HANDLER_CONTEXT create make end]
inherit inherit
@@ -23,7 +23,7 @@ feature {NONE} -- Initialization
feature {NONE} -- Routing feature {NONE} -- Routing
router: REQUEST_URI_TEMPLATE_ROUTER [H, C] router: REQUEST_URI_TEMPLATE_ROUTER_I [H, C]
;note ;note
copyright: "2011-2011, Eiffel Software and others" copyright: "2011-2011, Eiffel Software and others"