The http-logger is a noninteractive tool used to log interactions between Opera and the web servers it accesses.
This is a draft which has never been implemented.
Following is the grammar of the service, "http-logger":
PROTOCOL ::= (COMMAND | EVENT)* ;
##
# Commands (messages from debugger to debugging host)
#
COMMAND ::= SET-LOG-MODE
| GET-LOG-MODE
| GET-RESPONSE-BODY
;
SET-LOG-MODE ::= "<set-log-mode>" LOG-MODE-TYPE "</set-log-mode>" ;
GET-RESPONSE-BODY ::= "<get-response-body>"
REQUEST-ID
ENCODING?
DECODING?
"</get-response-body>"
;
GET-LOG-MODE ::= "<get-log-mode />" ;
###
# Events (messages from debugging host to debugger)
#
EVENT ::= REQUEST
| RESPONSE-HEADER
| RESPONSE-BODY
| LOG-MODE
;
REQUEST ::= "<request>"
REQUEST-ID
WINDOW-ID
RUNTIME-ID # this is perhaps not necessary if we have frame path
FRAME-PATH
TIME
METHOD
URL
PARSED-HEADERS
"</request>" ;
# The RESPONSE does not have it's own id, but refers to the generating REQUEST-ID
RESPONSE-HEADER ::= "<response-header>"
REQUEST-ID
TIME
MIME-TYPE
ENCODING
STATUS
RAW-HEADER
PARSED-HEADERS
"</response-header>" ;
# TODO: How should an event stream (e.g. server sent events) be represented? How about a really slow connection or big file?
RESPONSE-BODY ::= "<response-body>"
REQUEST-ID
TIME
BODY?
"</response-body>" ;
LOG-MODE ::= "<log-mode>" LOG-MODE-TYPE "</log-mode>" ;
##
# Other data types
#
BODY ::= "<body>"
ENCODING
DECODING
BODY-DATA
"</body>";
# REQUEST-ID is an identifier for the request; it is not necessarily unique across
# time, as it is just the memory address of the request object.
REQUEST-ID ::= "<request-id>" UNSIGNED "</request-id>" ;
# Timestamp of the message, in milliseconds since 1970-01-01 00:00 UTC
# (be sure not to rely on the time being correct - this is client time, and
# may be wildly different than the host time)
TIME ::= "<time>" FLOAT "</time>" ;
# Header of the request/response, i.e. the HTTP data up until the first
# occurence of CR+LF+CR+LF, inclusive.
RAW-HEADER ::= "<raw-header>" TEXT "</raw-header>" ;
PARSED-HEADERS ::= "<parsed-headers>" HEADER* "</parsed-headers>" ;
HEADER ::= "<header>"
HEADER-NAME
HEADER-VALUE
"</header>" ;
HEADER-NAME ::= "<header-name>" TEXT "</header-name>" ;
HEADER-VALUE ::= "<header-value>" TEXT "</header-value>" ;
ENCODING ::= "<encoding>" ENCODING-TYPE "</encoding>" ;
DECODING ::= "<decoding>" DECODING-TYPE "</decoding>" ;
BODY-DATA ::= "<body-data>" TEXT "</body-data>" ;
FLOAT ::= [0-9]+ "." [0-9]+ ;
# TODO: These names does not really reflect what is going on. At the very
# least they need an explanation.
LOG-MODE-TYPE ::= "profiling" | "logging" ;
# DECODING-TYPE is either
# "none", meaning raw data, or
# "used-by-opera", which is how Opera ended up decoding it
# TODO: How will Opera tell the client which encoding it actually used?
DECODING-TYPE ::= TEXT ;
ENCODING-TYPE ::= "none" | "base64" ;
FRAME-PATH ::= TEXT ;
MIME-TYPE ::= TEXT ;
STATUS ::= UNSIGNED ;
METHOD ::= TEXT ;
URL ::= TEXT ;
###
# From ecmascript-debugger-protocol.html
#
# The window ID is shared across scope. Notably, it's the same as in the ecmascript debugger.
# INTERNAL: The value is from Window::id
WINDOW-ID ::= "<window-id>" UNSIGNED "</window-id>" ;
UNSIGNED ::= [0-9]+ ;
RUNTIME-ID ::= UNSIGNED ;
TEXT ::= textual-data ;