Merge remote-tracking branch 'jocelynEWF/master'
Conflicts: examples/restbucks/restbucks-safe.ecf examples/restbucks/src/resource/order_handler.e library/server/request/router/src/misc/request_resource_handler_helper.e
This commit is contained in:
22
library/server/wsf/default/cgi-safe.ecf
Normal file
22
library/server/wsf/default/cgi-safe.ecf
Normal file
@@ -0,0 +1,22 @@
|
||||
<?xml version="1.0" encoding="ISO-8859-1"?>
|
||||
<system xmlns="http://www.eiffel.com/developers/xml/configuration-1-8-0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.eiffel.com/developers/xml/configuration-1-8-0 http://www.eiffel.com/developers/xml/configuration-1-8-0.xsd" name="default_cgi" uuid="A9137009-B5BA-4C58-BCD3-7753909918B5" library_target="default_cgi">
|
||||
<target name="default_cgi">
|
||||
<root all_classes="true"/>
|
||||
<file_rule>
|
||||
<exclude>/EIFGENs$</exclude>
|
||||
<exclude>/\.git$</exclude>
|
||||
<exclude>/\.svn$</exclude>
|
||||
</file_rule>
|
||||
<option warning="true" full_class_checking="true" is_attached_by_default="true" void_safety="all" syntax="provisional">
|
||||
</option>
|
||||
<library name="base" location="$ISE_LIBRARY\library\base\base-safe.ecf"/>
|
||||
<library name="time" location="$ISE_LIBRARY\library\time\time-safe.ecf"/>
|
||||
<library name="ewsgi" location="../../ewsgi/ewsgi-safe.ecf"/>
|
||||
<library name="wsf" location="../wsf-safe.ecf"/>
|
||||
<library name="connector_cgi" location="../../ewsgi/connectors/cgi/cgi-safe.ecf"/>
|
||||
<library name="error" location="..\..\..\error\error-safe.ecf"/>
|
||||
<library name="http" location="..\..\..\protocol\http\http-safe.ecf"/>
|
||||
<library name="encoder" location="..\..\..\text\encoder\encoder-safe.ecf" readonly="false"/>
|
||||
<cluster name="default_cgi" location="./cgi" recursive="true"/>
|
||||
</target>
|
||||
</system>
|
||||
22
library/server/wsf/default/cgi.ecf
Normal file
22
library/server/wsf/default/cgi.ecf
Normal file
@@ -0,0 +1,22 @@
|
||||
<?xml version="1.0" encoding="ISO-8859-1"?>
|
||||
<system xmlns="http://www.eiffel.com/developers/xml/configuration-1-8-0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.eiffel.com/developers/xml/configuration-1-8-0 http://www.eiffel.com/developers/xml/configuration-1-8-0.xsd" name="default_cgi" uuid="A9137009-B5BA-4C58-BCD3-7753909918B5" library_target="default_cgi">
|
||||
<target name="default_cgi">
|
||||
<root all_classes="true"/>
|
||||
<file_rule>
|
||||
<exclude>/EIFGENs$</exclude>
|
||||
<exclude>/\.git$</exclude>
|
||||
<exclude>/\.svn$</exclude>
|
||||
</file_rule>
|
||||
<option warning="true" full_class_checking="true" syntax="provisional">
|
||||
</option>
|
||||
<library name="base" location="$ISE_LIBRARY\library\base\base.ecf"/>
|
||||
<library name="time" location="$ISE_LIBRARY\library\time\time.ecf"/>
|
||||
<library name="ewsgi" location="../../ewsgi/ewsgi.ecf"/>
|
||||
<library name="wsf" location="../wsf.ecf"/>
|
||||
<library name="connector_cgi" location="../../ewsgi/connectors/cgi/cgi.ecf"/>
|
||||
<library name="error" location="..\..\..\error\error.ecf"/>
|
||||
<library name="http" location="..\..\..\protocol\http\http.ecf"/>
|
||||
<library name="encoder" location="..\..\..\text\encoder\encoder.ecf" readonly="false"/>
|
||||
<cluster name="default_cgi" location="./cgi" recursive="true"/>
|
||||
</target>
|
||||
</system>
|
||||
32
library/server/wsf/default/cgi/default_application.e
Normal file
32
library/server/wsf/default/cgi/default_application.e
Normal file
@@ -0,0 +1,32 @@
|
||||
note
|
||||
description: "Summary description for {DEFAULT_APPLICATION}."
|
||||
date: "$Date$"
|
||||
revision: "$Revision$"
|
||||
|
||||
deferred class
|
||||
DEFAULT_APPLICATION
|
||||
|
||||
inherit
|
||||
WSF_APPLICATION
|
||||
|
||||
feature {NONE} -- Initialization
|
||||
|
||||
make_and_launch
|
||||
local
|
||||
cgi: WGI_CGI_CONNECTOR
|
||||
do
|
||||
create cgi.make (Current)
|
||||
cgi.launch
|
||||
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
|
||||
26
library/server/wsf/default/nino-safe.ecf
Normal file
26
library/server/wsf/default/nino-safe.ecf
Normal file
@@ -0,0 +1,26 @@
|
||||
<?xml version="1.0" encoding="ISO-8859-1"?>
|
||||
<system xmlns="http://www.eiffel.com/developers/xml/configuration-1-8-0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.eiffel.com/developers/xml/configuration-1-8-0 http://www.eiffel.com/developers/xml/configuration-1-8-0.xsd" name="default_nino" uuid="ACBEDC97-956C-45F5-97E3-65A6D9987625" library_target="default_nino">
|
||||
<target name="default_nino">
|
||||
<root all_classes="true"/>
|
||||
<file_rule>
|
||||
<exclude>/EIFGENs$</exclude>
|
||||
<exclude>/\.git$</exclude>
|
||||
<exclude>/\.svn$</exclude>
|
||||
</file_rule>
|
||||
<option warning="true" full_class_checking="true" is_attached_by_default="true" void_safety="all" syntax="provisional">
|
||||
</option>
|
||||
<library name="base" location="$ISE_LIBRARY\library\base\base-safe.ecf"/>
|
||||
<library name="time" location="$ISE_LIBRARY\library\time\time-safe.ecf"/>
|
||||
<library name="ewsgi" location="../../ewsgi/ewsgi-safe.ecf"/>
|
||||
<library name="wsf" location="../wsf-safe.ecf"/>
|
||||
<library name="connector_nino" location="../../ewsgi/connectors/nino/nino-safe.ecf"/>
|
||||
<library name="nino" location="..\..\..\..\ext\server\nino\nino-safe.ecf" readonly="false">
|
||||
<renaming old_name="HTTP_CONSTANTS" new_name="NINO_HTTP_CONSTANTS"/>
|
||||
</library>
|
||||
|
||||
<library name="error" location="..\..\..\error\error-safe.ecf"/>
|
||||
<library name="http" location="..\..\..\protocol\http\http-safe.ecf"/>
|
||||
<library name="encoder" location="..\..\..\text\encoder\encoder-safe.ecf" readonly="false"/>
|
||||
<cluster name="default_nino" location="./nino" recursive="true"/>
|
||||
</target>
|
||||
</system>
|
||||
26
library/server/wsf/default/nino.ecf
Normal file
26
library/server/wsf/default/nino.ecf
Normal file
@@ -0,0 +1,26 @@
|
||||
<?xml version="1.0" encoding="ISO-8859-1"?>
|
||||
<system xmlns="http://www.eiffel.com/developers/xml/configuration-1-8-0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.eiffel.com/developers/xml/configuration-1-8-0 http://www.eiffel.com/developers/xml/configuration-1-8-0.xsd" name="default_nino" uuid="ACBEDC97-956C-45F5-97E3-65A6D9987625" library_target="default_nino">
|
||||
<target name="default_nino">
|
||||
<root all_classes="true"/>
|
||||
<file_rule>
|
||||
<exclude>/EIFGENs$</exclude>
|
||||
<exclude>/\.git$</exclude>
|
||||
<exclude>/\.svn$</exclude>
|
||||
</file_rule>
|
||||
<option warning="true" full_class_checking="true" syntax="provisional">
|
||||
</option>
|
||||
<library name="base" location="$ISE_LIBRARY\library\base\base.ecf"/>
|
||||
<library name="time" location="$ISE_LIBRARY\library\time\time.ecf"/>
|
||||
<library name="ewsgi" location="../../ewsgi/ewsgi.ecf"/>
|
||||
<library name="wsf" location="../wsf.ecf"/>
|
||||
<library name="connector_nino" location="../../ewsgi/connectors/nino/nino.ecf"/>
|
||||
<library name="nino" location="..\..\..\..\ext\server\nino\nino.ecf" readonly="false">
|
||||
<renaming old_name="HTTP_CONSTANTS" new_name="NINO_HTTP_CONSTANTS"/>
|
||||
</library>
|
||||
|
||||
<library name="error" location="..\..\..\error\error.ecf"/>
|
||||
<library name="http" location="..\..\..\protocol\http\http.ecf"/>
|
||||
<library name="encoder" location="..\..\..\text\encoder\encoder.ecf" readonly="false"/>
|
||||
<cluster name="default_nino" location="./nino" recursive="true"/>
|
||||
</target>
|
||||
</system>
|
||||
44
library/server/wsf/default/nino/default_application.e
Normal file
44
library/server/wsf/default/nino/default_application.e
Normal file
@@ -0,0 +1,44 @@
|
||||
note
|
||||
description: "Summary description for {DEFAULT_APPLICATION}."
|
||||
date: "$Date$"
|
||||
revision: "$Revision$"
|
||||
|
||||
deferred class
|
||||
DEFAULT_APPLICATION
|
||||
|
||||
inherit
|
||||
WSF_APPLICATION
|
||||
|
||||
feature {NONE} -- Initialization
|
||||
|
||||
make_and_launch
|
||||
local
|
||||
app: NINO_APPLICATION
|
||||
do
|
||||
port_number := 8080
|
||||
base_url := ""
|
||||
debug ("nino")
|
||||
print ("Example: start a Nino web server on port " + port_number.out +
|
||||
", %Nand reply Hello World for any request such as http://localhost:" + port_number.out + "/" + base_url + "%N")
|
||||
end
|
||||
create app.make_custom (agent wgi_execute, base_url)
|
||||
app.listen (port_number)
|
||||
end
|
||||
|
||||
port_number: INTEGER
|
||||
|
||||
base_url: STRING
|
||||
|
||||
invariant
|
||||
port_number_valid: port_number > 0
|
||||
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
|
||||
13
library/server/wsf/src/cgi_meta_names.e
Normal file
13
library/server/wsf/src/cgi_meta_names.e
Normal file
@@ -0,0 +1,13 @@
|
||||
note
|
||||
description: "Summary description for {WSF_META_NAMES}."
|
||||
author: ""
|
||||
date: "$Date$"
|
||||
revision: "$Revision$"
|
||||
|
||||
class
|
||||
CGI_META_NAMES
|
||||
|
||||
inherit
|
||||
WGI_META_NAMES
|
||||
|
||||
end
|
||||
143
library/server/wsf/src/request/value/wsf_multiple_string_value.e
Normal file
143
library/server/wsf/src/request/value/wsf_multiple_string_value.e
Normal file
@@ -0,0 +1,143 @@
|
||||
note
|
||||
description: "Summary description for {WSF_MULTIPLE_STRING_VALUE}."
|
||||
author: ""
|
||||
date: "$Date$"
|
||||
revision: "$Revision$"
|
||||
|
||||
class
|
||||
WSF_MULTIPLE_STRING_VALUE
|
||||
|
||||
inherit
|
||||
WSF_VALUE
|
||||
|
||||
ITERABLE [WSF_STRING_VALUE]
|
||||
|
||||
create
|
||||
make_with_value,
|
||||
make_with_array,
|
||||
make_with_string
|
||||
|
||||
feature {NONE} -- Initialization
|
||||
|
||||
make_with_value (a_value: WSF_VALUE)
|
||||
do
|
||||
name := a_value.name
|
||||
create {LINKED_LIST [WSF_STRING_VALUE]} string_values.make
|
||||
add_value (a_value)
|
||||
end
|
||||
|
||||
make_with_array (arr: ARRAY [WSF_VALUE])
|
||||
require
|
||||
arr_not_empty: not arr.is_empty
|
||||
all_same_name: across arr as c all c.item.name.same_string (arr[arr.lower].name) end
|
||||
local
|
||||
i,up: INTEGER
|
||||
do
|
||||
up := arr.upper
|
||||
i := arr.lower
|
||||
make_with_value (arr[i])
|
||||
from
|
||||
i := i + 1
|
||||
until
|
||||
i > up
|
||||
loop
|
||||
add_value (arr[i])
|
||||
i := i + 1
|
||||
end
|
||||
end
|
||||
|
||||
make_with_string (a_name: like name; a_string: READABLE_STRING_32)
|
||||
do
|
||||
make_with_value (create {WSF_STRING_VALUE}.make (a_name, a_string))
|
||||
end
|
||||
|
||||
feature -- Access
|
||||
|
||||
name: READABLE_STRING_32
|
||||
|
||||
string_values: LIST [WSF_STRING_VALUE]
|
||||
|
||||
first_string_value: WSF_STRING_VALUE
|
||||
do
|
||||
Result := string_values.first
|
||||
end
|
||||
|
||||
feature -- Traversing
|
||||
|
||||
new_cursor: ITERATION_CURSOR [WSF_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: WSF_VALUE)
|
||||
require
|
||||
same_name: a_value.name.same_string (name)
|
||||
do
|
||||
if attached {WSF_STRING_VALUE} a_value as sval then
|
||||
add_string_value (sval)
|
||||
elseif attached {WSF_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: WSF_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
|
||||
91
library/server/wsf/src/request/value/wsf_string_value.e
Normal file
91
library/server/wsf/src/request/value/wsf_string_value.e
Normal file
@@ -0,0 +1,91 @@
|
||||
note
|
||||
description: "Summary description for {WSF_STRING_VALUE}."
|
||||
author: ""
|
||||
date: "$Date$"
|
||||
revision: "$Revision$"
|
||||
|
||||
class
|
||||
WSF_STRING_VALUE
|
||||
|
||||
inherit
|
||||
WSF_VALUE
|
||||
|
||||
create
|
||||
make
|
||||
|
||||
convert
|
||||
as_string: {READABLE_STRING_32, STRING_32}
|
||||
|
||||
feature {NONE} -- Initialization
|
||||
|
||||
make (a_name: READABLE_STRING_8; a_string: READABLE_STRING_8)
|
||||
do
|
||||
name := url_decoded_string (a_name)
|
||||
string := url_decoded_string (a_string)
|
||||
|
||||
url_encoded_name := a_name
|
||||
url_encoded_string := a_string
|
||||
end
|
||||
|
||||
feature -- Access
|
||||
|
||||
name: READABLE_STRING_32
|
||||
|
||||
string: READABLE_STRING_32
|
||||
|
||||
url_encoded_name: READABLE_STRING_32
|
||||
|
||||
url_encoded_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
|
||||
|
||||
feature {NONE} -- Implementation
|
||||
|
||||
url_decoded_string (s: READABLE_STRING_8): READABLE_STRING_32
|
||||
-- Decoded url-encoded string `s'
|
||||
do
|
||||
Result := url_encoder.decoded_string (s)
|
||||
end
|
||||
|
||||
url_encoder: URL_ENCODER
|
||||
once
|
||||
create Result
|
||||
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
|
||||
59
library/server/wsf/src/request/wsf_value.e
Normal file
59
library/server/wsf/src/request/wsf_value.e
Normal file
@@ -0,0 +1,59 @@
|
||||
note
|
||||
description: "Summary description for {WSF_VALUE}."
|
||||
author: ""
|
||||
date: "$Date$"
|
||||
revision: "$Revision$"
|
||||
|
||||
deferred class
|
||||
WSF_VALUE
|
||||
|
||||
inherit
|
||||
DEBUG_OUTPUT
|
||||
|
||||
convert
|
||||
as_string: {READABLE_STRING_32, STRING_32}
|
||||
|
||||
feature -- Access
|
||||
|
||||
name: READABLE_STRING_32
|
||||
-- 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 -- Status report
|
||||
|
||||
debug_output: STRING
|
||||
-- String that should be displayed in debugger to represent `Current'.
|
||||
do
|
||||
create Result.make_from_string (name.as_string_8 + "=" + as_string.as_string_8)
|
||||
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
|
||||
66
library/server/wsf/src/support/wsf_error.e
Normal file
66
library/server/wsf/src/support/wsf_error.e
Normal file
@@ -0,0 +1,66 @@
|
||||
note
|
||||
description: "Summary description for {WSF_ERROR}."
|
||||
legal: "See notice at end of class."
|
||||
status: "See notice at end of class."
|
||||
date: "$Date$"
|
||||
revision: "$Revision$"
|
||||
|
||||
class
|
||||
WSF_ERROR
|
||||
|
||||
inherit
|
||||
ERROR
|
||||
|
||||
HTTP_STATUS_CODE_MESSAGES
|
||||
|
||||
create
|
||||
make
|
||||
|
||||
feature {NONE} -- Initialization
|
||||
|
||||
make (a_code: INTEGER)
|
||||
do
|
||||
code := a_code
|
||||
name := "HTTP Error"
|
||||
if attached http_status_code_message (a_code) as m then
|
||||
name := m
|
||||
end
|
||||
end
|
||||
|
||||
feature -- Access
|
||||
|
||||
code: INTEGER
|
||||
|
||||
name: STRING
|
||||
|
||||
message: detachable STRING_32
|
||||
|
||||
feature -- Element change
|
||||
|
||||
set_message (m: like message)
|
||||
-- Set `message' to `m'
|
||||
require
|
||||
m_attached: m /= Void
|
||||
do
|
||||
message := m
|
||||
end
|
||||
|
||||
feature -- Visitor
|
||||
|
||||
process (a_visitor: ERROR_VISITOR)
|
||||
-- Process Current using `a_visitor'.
|
||||
do
|
||||
a_visitor.process_error (Current)
|
||||
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
|
||||
42
library/server/wsf/src/support/wsf_header.e
Normal file
42
library/server/wsf/src/support/wsf_header.e
Normal file
@@ -0,0 +1,42 @@
|
||||
note
|
||||
description: "[
|
||||
The class provides an easy way to build HTTP header.
|
||||
|
||||
You will also find some helper feature to help coding most common usage
|
||||
|
||||
Please, have a look at constants classes such as
|
||||
HTTP_MIME_TYPES
|
||||
HTTP_HEADER_NAMES
|
||||
HTTP_STATUS_CODE
|
||||
HTTP_REQUEST_METHODS
|
||||
(or HTTP_CONSTANTS which groups them for convenience)
|
||||
|
||||
Note the return status code is not part of the HTTP header
|
||||
However you can set the "Status: " header line if you want
|
||||
]"
|
||||
legal: "See notice at end of class."
|
||||
status: "See notice at end of class."
|
||||
date: "$Date$"
|
||||
revision: "$Revision$"
|
||||
|
||||
class
|
||||
WSF_HEADER
|
||||
|
||||
inherit
|
||||
EWF_HEADER
|
||||
|
||||
create
|
||||
make,
|
||||
make_with_count
|
||||
|
||||
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
|
||||
32
library/server/wsf/src/wsf_application.e
Normal file
32
library/server/wsf/src/wsf_application.e
Normal file
@@ -0,0 +1,32 @@
|
||||
note
|
||||
description: "Objects that ..."
|
||||
date: "$Date$"
|
||||
revision: "$Revision$"
|
||||
|
||||
deferred class
|
||||
WSF_APPLICATION
|
||||
|
||||
inherit
|
||||
WGI_APPLICATION
|
||||
rename
|
||||
execute as wgi_execute
|
||||
end
|
||||
|
||||
feature -- Execution
|
||||
|
||||
execute (req: WSF_REQUEST; res: WSF_RESPONSE)
|
||||
-- Execute the request
|
||||
-- See `req.input' for input stream
|
||||
-- `req.meta_variables' for the CGI meta variable
|
||||
-- and `res' for output buffer
|
||||
deferred
|
||||
end
|
||||
|
||||
feature -- WGI Execution
|
||||
|
||||
wgi_execute (req: WGI_REQUEST; res: WGI_RESPONSE_BUFFER)
|
||||
do
|
||||
execute (req, res)
|
||||
end
|
||||
|
||||
end
|
||||
1499
library/server/wsf/src/wsf_request.e
Normal file
1499
library/server/wsf/src/wsf_request.e
Normal file
File diff suppressed because it is too large
Load Diff
164
library/server/wsf/src/wsf_response.e
Normal file
164
library/server/wsf/src/wsf_response.e
Normal file
@@ -0,0 +1,164 @@
|
||||
note
|
||||
description: "[
|
||||
Summary description for {WSF_RESPONSE}.
|
||||
]"
|
||||
date: "$Date$"
|
||||
revision: "$Revision$"
|
||||
|
||||
class
|
||||
WSF_RESPONSE
|
||||
|
||||
create {WSF_APPLICATION}
|
||||
make_from_wgi
|
||||
|
||||
convert
|
||||
make_from_wgi ({WGI_RESPONSE_BUFFER})
|
||||
|
||||
feature {NONE} -- Initialization
|
||||
|
||||
make_from_wgi (r: WGI_RESPONSE_BUFFER)
|
||||
do
|
||||
wgi_response := r
|
||||
end
|
||||
|
||||
wgi_response: WGI_RESPONSE_BUFFER
|
||||
|
||||
--feature {WSF_APPLICATION} -- Commit
|
||||
|
||||
-- commit
|
||||
-- -- Commit the current response
|
||||
-- do
|
||||
-- wgi_response.commit
|
||||
-- ensure
|
||||
-- status_is_set: status_is_set
|
||||
-- header_committed: header_committed
|
||||
-- message_committed: message_committed
|
||||
-- end
|
||||
|
||||
feature -- Status report
|
||||
|
||||
header_committed: BOOLEAN
|
||||
-- Header committed?
|
||||
do
|
||||
Result := wgi_response.header_committed
|
||||
end
|
||||
|
||||
message_committed: BOOLEAN
|
||||
-- Message committed?
|
||||
do
|
||||
Result := wgi_response.message_committed
|
||||
end
|
||||
|
||||
message_writable: BOOLEAN
|
||||
-- Can message be written?
|
||||
do
|
||||
Result := wgi_response.message_writable
|
||||
end
|
||||
|
||||
--feature {WGI_RESPONSE_BUFFER} -- Core output operation
|
||||
|
||||
-- write (s: READABLE_STRING_8)
|
||||
-- -- Send the string `s'
|
||||
-- -- this can be used for header and body
|
||||
-- do
|
||||
-- wgi_response.write (s)
|
||||
-- end
|
||||
|
||||
feature -- Status setting
|
||||
|
||||
status_is_set: BOOLEAN
|
||||
-- Is status set?
|
||||
do
|
||||
Result := wgi_response.status_is_set
|
||||
end
|
||||
|
||||
set_status_code (a_code: INTEGER)
|
||||
-- Set response status code
|
||||
-- Should be done before sending any data back to the client
|
||||
require
|
||||
status_not_set: not status_is_set
|
||||
header_not_committed: not header_committed
|
||||
do
|
||||
wgi_response.set_status_code (a_code)
|
||||
ensure
|
||||
status_code_set: status_code = a_code
|
||||
status_set: status_is_set
|
||||
end
|
||||
|
||||
status_code: INTEGER
|
||||
-- Response status
|
||||
do
|
||||
Result := wgi_response.status_code
|
||||
end
|
||||
|
||||
feature -- Header output operation
|
||||
|
||||
write_headers_string (a_headers: READABLE_STRING_8)
|
||||
require
|
||||
status_set: status_is_set
|
||||
header_not_committed: not header_committed
|
||||
do
|
||||
wgi_response.write_headers_string (a_headers)
|
||||
ensure
|
||||
status_set: status_is_set
|
||||
header_committed: header_committed
|
||||
message_writable: message_writable
|
||||
end
|
||||
|
||||
write_header (a_status_code: INTEGER; a_headers: detachable ARRAY [TUPLE [key: READABLE_STRING_8; value: READABLE_STRING_8]])
|
||||
-- Send headers with status `a_status', and headers from `a_headers'
|
||||
require
|
||||
status_not_set: not status_is_set
|
||||
header_not_committed: not header_committed
|
||||
do
|
||||
wgi_response.write_header (a_status_code, a_headers)
|
||||
ensure
|
||||
header_committed: header_committed
|
||||
status_set: status_is_set
|
||||
message_writable: message_writable
|
||||
end
|
||||
|
||||
feature -- Output operation
|
||||
|
||||
write_string (s: READABLE_STRING_8)
|
||||
-- Send the string `s'
|
||||
require
|
||||
message_writable: message_writable
|
||||
do
|
||||
wgi_response.write_string (s)
|
||||
end
|
||||
|
||||
write_substring (s: READABLE_STRING_8; a_begin_index, a_end_index: INTEGER)
|
||||
-- Send the substring `s[a_begin_index:a_end_index]'
|
||||
require
|
||||
message_writable: message_writable
|
||||
do
|
||||
wgi_response.write_substring (s, a_begin_index, a_end_index)
|
||||
end
|
||||
|
||||
write_file_content (fn: READABLE_STRING_8)
|
||||
-- Send the content of file `fn'
|
||||
require
|
||||
message_writable: message_writable
|
||||
do
|
||||
wgi_response.write_file_content (fn)
|
||||
end
|
||||
|
||||
flush
|
||||
-- Flush if it makes sense
|
||||
do
|
||||
wgi_response.flush
|
||||
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
|
||||
213
library/server/wsf/tests/test_wsf_request.e
Normal file
213
library/server/wsf/tests/test_wsf_request.e
Normal file
@@ -0,0 +1,213 @@
|
||||
note
|
||||
description: "[
|
||||
Eiffel tests that can be executed by testing tool.
|
||||
]"
|
||||
author: "EiffelStudio test wizard"
|
||||
date: "$Date$"
|
||||
revision: "$Revision$"
|
||||
testing: "type/manual"
|
||||
|
||||
class
|
||||
TEST_EWSGI_REQUEST
|
||||
|
||||
inherit
|
||||
EQA_TEST_SET
|
||||
redefine
|
||||
on_prepare,
|
||||
on_clean
|
||||
end
|
||||
|
||||
WSF_APPLICATION
|
||||
undefine
|
||||
default_create
|
||||
end
|
||||
|
||||
feature {NONE} -- Events
|
||||
|
||||
web_app: detachable NINO_APPLICATION
|
||||
|
||||
port_number: INTEGER
|
||||
base_url: detachable STRING
|
||||
|
||||
on_prepare
|
||||
-- <Precursor>
|
||||
local
|
||||
app: NINO_APPLICATION
|
||||
wt: WORKER_THREAD
|
||||
e: EXECUTION_ENVIRONMENT
|
||||
do
|
||||
port_number := 8087
|
||||
base_url := "test/"
|
||||
create app.make_custom (agent wgi_execute, base_url)
|
||||
web_app := app
|
||||
|
||||
create wt.make (agent app.listen (port_number))
|
||||
wt.launch
|
||||
|
||||
create e
|
||||
e.sleep (1_000_000_000 * 5)
|
||||
end
|
||||
|
||||
execute (req: WSF_REQUEST; res: WSF_RESPONSE)
|
||||
local
|
||||
q: detachable STRING_32
|
||||
do
|
||||
if attached req.request_uri as l_uri then
|
||||
if l_uri.starts_with (test_url ("get/01")) then
|
||||
res.write_header (200, <<["Content-Type", "text/plain"]>>)
|
||||
res.write_string ("get-01")
|
||||
create q.make_empty
|
||||
|
||||
across
|
||||
req.query_parameters as qcur
|
||||
loop
|
||||
if not q.is_empty then
|
||||
q.append_character ('&')
|
||||
end
|
||||
q.append (qcur.item.name.as_string_32 + "=" + qcur.item.as_string)
|
||||
end
|
||||
if not q.is_empty then
|
||||
res.write_string ("(" + q + ")")
|
||||
end
|
||||
elseif l_uri.starts_with (test_url ("post/01")) then
|
||||
res.write_header (200, <<["Content-Type", "text/plain"]>>)
|
||||
res.write_string ("post-01")
|
||||
create q.make_empty
|
||||
|
||||
across
|
||||
req.query_parameters as qcur
|
||||
loop
|
||||
if not q.is_empty then
|
||||
q.append_character ('&')
|
||||
end
|
||||
q.append (qcur.item.name.as_string_32 + "=" + qcur.item.as_string)
|
||||
end
|
||||
|
||||
if not q.is_empty then
|
||||
res.write_string ("(" + q + ")")
|
||||
end
|
||||
|
||||
create q.make_empty
|
||||
|
||||
|
||||
across
|
||||
req.form_data_parameters as fcur
|
||||
loop
|
||||
if not q.is_empty then
|
||||
q.append_character ('&')
|
||||
end
|
||||
q.append (fcur.item.name.as_string_32 + "=" + fcur.item.as_string)
|
||||
end
|
||||
|
||||
if not q.is_empty then
|
||||
res.write_string (" : " + q )
|
||||
end
|
||||
else
|
||||
res.write_header (200, <<["Content-Type", "text/plain"]>>)
|
||||
res.write_string ("Hello")
|
||||
end
|
||||
else
|
||||
res.write_header (200, <<["Content-Type", "text/plain"]>>)
|
||||
res.write_string ("Bye")
|
||||
end
|
||||
end
|
||||
|
||||
test_url (a_query_url: READABLE_STRING_8): READABLE_STRING_8
|
||||
local
|
||||
b: like base_url
|
||||
do
|
||||
b := base_url
|
||||
if b = Void then
|
||||
b := ""
|
||||
end
|
||||
Result := "/" + b + a_query_url
|
||||
end
|
||||
|
||||
on_clean
|
||||
-- <Precursor>
|
||||
do
|
||||
if attached web_app as app then
|
||||
app.shutdown
|
||||
end
|
||||
end
|
||||
|
||||
http_session: detachable HTTP_CLIENT_SESSION
|
||||
|
||||
get_http_session
|
||||
local
|
||||
h: LIBCURL_HTTP_CLIENT
|
||||
b: like base_url
|
||||
do
|
||||
create h.make
|
||||
b := base_url
|
||||
if b = Void then
|
||||
b := ""
|
||||
end
|
||||
if attached {HTTP_CLIENT_SESSION} h.new_session ("localhost:" + port_number.out + "/" + b) as sess then
|
||||
http_session := sess
|
||||
sess.set_timeout (-1)
|
||||
sess.set_connect_timeout (-1)
|
||||
end
|
||||
end
|
||||
|
||||
test_get_request (a_url: READABLE_STRING_8; ctx: detachable HTTP_CLIENT_REQUEST_CONTEXT; a_expected_body: READABLE_STRING_8)
|
||||
do
|
||||
get_http_session
|
||||
if attached http_session as sess then
|
||||
if attached sess.get (a_url, ctx) as res and then not res.error_occurred and then attached res.body as l_body then
|
||||
assert ("Good answer got=%""+l_body+"%" expected=%""+a_expected_body+"%"", l_body.same_string (a_expected_body))
|
||||
else
|
||||
assert ("Request %""+a_url+"%" failed", False)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
test_post_request (a_url: READABLE_STRING_8; ctx: detachable HTTP_CLIENT_REQUEST_CONTEXT; a_expected_body: READABLE_STRING_8)
|
||||
do
|
||||
get_http_session
|
||||
if attached http_session as sess then
|
||||
if attached sess.post (a_url, ctx, Void) as res and then not res.error_occurred and then attached res.body as l_body then
|
||||
assert ("Good answer got=%""+l_body+"%" expected=%""+a_expected_body+"%"", l_body.same_string (a_expected_body))
|
||||
else
|
||||
assert ("Request %""+a_url+"%" failed", False)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
feature -- Test routines
|
||||
|
||||
test_get_request_01
|
||||
-- New test routine
|
||||
do
|
||||
get_http_session
|
||||
if attached http_session as sess then
|
||||
test_get_request ("get/01", Void, "get-01")
|
||||
test_get_request ("get/01/?foo=bar", Void, "get-01(foo=bar)")
|
||||
test_get_request ("get/01/?foo=bar&abc=def", Void, "get-01(foo=bar&abc=def)")
|
||||
test_get_request ("get/01/?lst=a&lst=b", Void, "get-01(lst=[a,b])")
|
||||
else
|
||||
assert ("not_implemented", False)
|
||||
end
|
||||
end
|
||||
|
||||
test_post_request_01
|
||||
-- New test routine
|
||||
local
|
||||
ctx: HTTP_CLIENT_REQUEST_CONTEXT
|
||||
do
|
||||
get_http_session
|
||||
if attached http_session as sess then
|
||||
create ctx.make
|
||||
ctx.add_form_data_parameter ("id", "123")
|
||||
test_post_request ("post/01", ctx, "post-01 : id=123")
|
||||
test_post_request ("post/01/?foo=bar", ctx, "post-01(foo=bar) : id=123")
|
||||
test_post_request ("post/01/?foo=bar&abc=def", ctx, "post-01(foo=bar&abc=def) : id=123")
|
||||
test_post_request ("post/01/?lst=a&lst=b", ctx, "post-01(lst=[a,b]) : id=123")
|
||||
else
|
||||
assert ("not_implemented", False)
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
|
||||
21
library/server/wsf/tests/tests-safe.ecf
Normal file
21
library/server/wsf/tests/tests-safe.ecf
Normal file
@@ -0,0 +1,21 @@
|
||||
<?xml version="1.0" encoding="ISO-8859-1"?>
|
||||
<system xmlns="http://www.eiffel.com/developers/xml/configuration-1-8-0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.eiffel.com/developers/xml/configuration-1-8-0 http://www.eiffel.com/developers/xml/configuration-1-8-0.xsd" name="tests" uuid="CA72F5B3-E608-4FA5-8F05-A812441DB961">
|
||||
<target name="tests">
|
||||
<root class="ANY" feature="default_create"/>
|
||||
<file_rule>
|
||||
<exclude>/.git$</exclude>
|
||||
<exclude>/EIFGENs$</exclude>
|
||||
<exclude>/.svn$</exclude>
|
||||
</file_rule>
|
||||
<option warning="true" full_class_checking="true" is_attached_by_default="true" void_safety="all" syntax="provisional">
|
||||
</option>
|
||||
<setting name="concurrency" value="thread"/>
|
||||
<library name="base" location="$ISE_LIBRARY\library\base\base-safe.ecf"/>
|
||||
<library name="connector_nino" location="..\..\ewsgi\connectors\nino\nino-safe.ecf" readonly="false"/>
|
||||
<library name="wsf" location="..\wsf-safe.ecf" readonly="false"/>
|
||||
<library name="http_client" location="..\..\..\client\http_client\http_client-safe.ecf"/>
|
||||
<library name="testing" location="$ISE_LIBRARY\library\testing\testing-safe.ecf"/>
|
||||
<library name="thread" location="$ISE_LIBRARY\library\thread\thread-safe.ecf"/>
|
||||
<tests name="src" location=".\" recursive="false"/>
|
||||
</target>
|
||||
</system>
|
||||
21
library/server/wsf/tests/tests.ecf
Normal file
21
library/server/wsf/tests/tests.ecf
Normal file
@@ -0,0 +1,21 @@
|
||||
<?xml version="1.0" encoding="ISO-8859-1"?>
|
||||
<system xmlns="http://www.eiffel.com/developers/xml/configuration-1-8-0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.eiffel.com/developers/xml/configuration-1-8-0 http://www.eiffel.com/developers/xml/configuration-1-8-0.xsd" name="tests" uuid="CA72F5B3-E608-4FA5-8F05-A812441DB961">
|
||||
<target name="tests">
|
||||
<root class="ANY" feature="default_create"/>
|
||||
<file_rule>
|
||||
<exclude>/.git$</exclude>
|
||||
<exclude>/EIFGENs$</exclude>
|
||||
<exclude>/.svn$</exclude>
|
||||
</file_rule>
|
||||
<option warning="true" full_class_checking="true" void_safety="none" syntax="provisional">
|
||||
</option>
|
||||
<setting name="concurrency" value="none"/>
|
||||
<library name="base" location="$ISE_LIBRARY/library/base/base.ecf"/>
|
||||
<library name="dft_nino" location="..\default\nino.ecf"/>
|
||||
<library name="wsf" location="..\wsf.ecf"/>
|
||||
<library name="http_client" location="..\..\..\client\http_client\http_client.ecf"/>
|
||||
<library name="testing" location="$ISE_LIBRARY/library/testing/testing.ecf"/>
|
||||
<library name="thread" location="$ISE_LIBRARY\library\thread\thread-safe.ecf"/>
|
||||
<tests name="src" location="." recursive="true"/>
|
||||
</target>
|
||||
</system>
|
||||
20
library/server/wsf/wsf-safe.ecf
Normal file
20
library/server/wsf/wsf-safe.ecf
Normal file
@@ -0,0 +1,20 @@
|
||||
<?xml version="1.0" encoding="ISO-8859-1"?>
|
||||
<system xmlns="http://www.eiffel.com/developers/xml/configuration-1-9-0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.eiffel.com/developers/xml/configuration-1-9-0 http://www.eiffel.com/developers/xml/configuration-1-9-0.xsd" name="wsf" uuid="A37CE5AA-4D2A-4441-BC6A-0A1D7EC49647" library_target="wsf">
|
||||
<target name="wsf">
|
||||
<root all_classes="true"/>
|
||||
<file_rule>
|
||||
<exclude>/.git$</exclude>
|
||||
<exclude>/EIFGENs$</exclude>
|
||||
<exclude>/.svn$</exclude>
|
||||
</file_rule>
|
||||
<option warning="true" full_class_checking="true" is_attached_by_default="true" void_safety="all" syntax="provisional">
|
||||
</option>
|
||||
<library name="base" location="$ISE_LIBRARY\library\base\base-safe.ecf"/>
|
||||
<library name="ewsgi" location="..\ewsgi\ewsgi-safe.ecf"/>
|
||||
<library name="time" location="$ISE_LIBRARY\library\time\time-safe.ecf"/>
|
||||
<library name="error" location="..\..\error\error-safe.ecf"/>
|
||||
<library name="http" location="..\..\protocol\http\http-safe.ecf"/>
|
||||
<library name="encoder" location="..\..\text\encoder\encoder-safe.ecf"/>
|
||||
<cluster name="src" location=".\src" recursive="true"/>
|
||||
</target>
|
||||
</system>
|
||||
20
library/server/wsf/wsf.ecf
Normal file
20
library/server/wsf/wsf.ecf
Normal file
@@ -0,0 +1,20 @@
|
||||
<?xml version="1.0" encoding="ISO-8859-1"?>
|
||||
<system xmlns="http://www.eiffel.com/developers/xml/configuration-1-8-0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.eiffel.com/developers/xml/configuration-1-8-0 http://www.eiffel.com/developers/xml/configuration-1-8-0.xsd" name="wsf" uuid="A37CE5AA-4D2A-4441-BC6A-0A1D7EC49647" library_target="wsf">
|
||||
<target name="wsf">
|
||||
<root all_classes="true"/>
|
||||
<file_rule>
|
||||
<exclude>/.git$</exclude>
|
||||
<exclude>/EIFGENs$</exclude>
|
||||
<exclude>/.svn$</exclude>
|
||||
</file_rule>
|
||||
<option warning="true" full_class_checking="true" void_safety="none" syntax="standard">
|
||||
</option>
|
||||
<library name="base" location="$ISE_LIBRARY/library/base/base.ecf"/>
|
||||
<library name="ewsgi" location="..\ewsgi\ewsgi.ecf"/>
|
||||
<library name="time" location="$ISE_LIBRARY\library\time\time.ecf"/>
|
||||
<library name="error" location="..\..\error\error.ecf"/>
|
||||
<library name="http" location="..\..\protocol\http\http.ecf"/>
|
||||
<library name="encoder" location="..\..\text\encoder\encoder.ecf"/>
|
||||
<cluster name="src" location=".\src" recursive="true"/>
|
||||
</target>
|
||||
</system>
|
||||
Reference in New Issue
Block a user