1 // Test nsITraceableChannel interface.
2 // Replace original listener with TracingListener that modifies body of HTTP
3 // response. Make sure that body received by original channel's listener
4 // is correctly modified.
6 do_import_script("netwerk/test/httpserver/httpd.js");
9 var originalBody
= "original http response body";
10 var replacedBody
= "replaced http response body";
12 function TracingListener() {}
14 TracingListener
.prototype = {
16 // Replace received response body.
17 onDataAvailable: function(request
, context
, inputStream
,
19 dump("*** tracing listener onDataAvailable\n");
20 var binaryInputStream
= Cc
["@mozilla.org/binaryinputstream;1"].
21 createInstance(Components
.interfaces
.nsIBinaryInputStream
);
22 binaryInputStream
.setInputStream(inputStream
);
24 var data
= binaryInputStream
.readBytes(count
);
25 var origBody
= originalBody
.substr(offset
, count
);
26 do_check_eq(origBody
, data
);
28 var storageStream
= Cc
["@mozilla.org/storagestream;1"].
29 createInstance(Components
.interfaces
.nsIStorageStream
);
30 var binaryOutputStream
= Cc
["@mozilla.org/binaryoutputstream;1"].
31 createInstance(Components
.interfaces
.nsIBinaryOutputStream
);
33 storageStream
.init(8192, 100, null);
34 binaryOutputStream
.setOutputStream(storageStream
.getOutputStream(0));
36 var newBody
= replacedBody
.substr(offset
, count
);
37 binaryOutputStream
.writeBytes(newBody
, newBody
.length
);
39 this.listener
.onDataAvailable(request
, context
,
40 storageStream
.newInputStream(0), 0,
44 onStartRequest: function(request
, context
) {
45 this.listener
.onStartRequest(request
, context
);
47 // Make sure listener can't be replaced after OnStartRequest was called.
48 request
.QueryInterface(Components
.interfaces
.nsITraceableChannel
);
50 var newListener
= new TracingListener();
51 newListener
.listener
= request
.setNewListener(newListener
);
55 do_throw("replaced channel's listener during onStartRequest.");
58 onStopRequest: function(request
, context
, statusCode
) {
59 this.listener
.onStopRequest(request
, context
, statusCode
);
64 QueryInterface: function(iid
) {
65 if (iid
.equals(Components
.interfaces
.nsIStreamListener
) ||
66 iid
.equals(Components
.interfaces
.nsIRequestObserver
) ||
67 iid
.equals(Components
.interfaces
.nsISupports
)
70 throw Components
.results
.NS_NOINTERFACE
;
77 function HttpResponseExaminer() {}
79 HttpResponseExaminer
.prototype = {
80 register: function() {
81 Cc
["@mozilla.org/observer-service;1"].
82 getService(Components
.interfaces
.nsIObserverService
).
83 addObserver(this, "http-on-examine-response", true);
86 // Replace channel's listener.
87 observe: function(subject
, topic
, data
) {
89 subject
.QueryInterface(Components
.interfaces
.nsITraceableChannel
);
90 var newListener
= new TracingListener();
91 newListener
.listener
= subject
.setNewListener(newListener
);
93 do_throw("can't replace listener" + e
);
97 QueryInterface: function(iid
) {
98 if (iid
.equals(Components
.interfaces
.nsIObserver
) ||
99 iid
.equals(Components
.interfaces
.nsISupportsWeakReference
) ||
100 iid
.equals(Components
.interfaces
.nsISupports
))
102 throw Components
.results
.NS_NOINTERFACE
;
106 function test_handler(metadata
, response
) {
107 response
.setHeader("Content-Type", "text/html", false);
108 response
.setStatusLine(metadata
.httpVersion
, 200, "OK");
109 response
.bodyOutputStream
.write(originalBody
, originalBody
.length
);
112 function make_channel(url
) {
113 var ios
= Cc
["@mozilla.org/network/io-service;1"].
114 getService(Ci
.nsIIOService
);
115 return ios
.newChannel(url
, null, null).
116 QueryInterface(Components
.interfaces
.nsIHttpChannel
);
119 // Check if received body is correctly modified.
120 function get_data(request
, input
, ctx
) {
121 do_check_eq(replacedBody
, input
);
124 function run_test() {
125 var observer
= new HttpResponseExaminer();
128 httpserver
= new nsHttpServer();
129 httpserver
.registerPathHandler("/testdir", test_handler
);
130 httpserver
.start(4444);
132 var channel
= make_channel("http://localhost:4444/testdir");
133 channel
.asyncOpen(new ChannelListener(get_data
), null);