]> git.proxmox.com Git - ceph.git/blame - ceph/src/jaegertracing/thrift/lib/as3/src/org/apache/thrift/transport/TFullDuplexHttpClient.as
buildsys: switch source download to quincy
[ceph.git] / ceph / src / jaegertracing / thrift / lib / as3 / src / org / apache / thrift / transport / TFullDuplexHttpClient.as
CommitLineData
f67539c2
TL
1/*
2 * Licensed to the Apache Software Foundation (ASF) under one
3 * or more contributor license agreements. See the NOTICE file
4 * distributed with this work for additional information
5 * regarding copyright ownership. The ASF licenses this file
6 * to you under the Apache License, Version 2.0 (the
7 * "License"); you may not use this file except in compliance
8 * with the License. You may obtain a copy of the License at
9 *
10 * http://www.apache.org/licenses/LICENSE-2.0
11 *
12 * Unless required by applicable law or agreed to in writing,
13 * software distributed under the License is distributed on an
14 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15 * KIND, either express or implied. See the License for the
16 * specific language governing permissions and limitations
17 * under the License.
18 */
19
20package org.apache.thrift.transport
21{
22
23 import flash.errors.EOFError;
24 import flash.events.Event;
25 import flash.events.IOErrorEvent;
26 import flash.events.ProgressEvent;
27 import flash.events.SecurityErrorEvent;
28 import flash.net.URLLoader;
29 import flash.net.URLLoaderDataFormat;
30 import flash.net.URLRequest;
31 import flash.net.URLRequestMethod;
32 import flash.utils.IDataInput;
33 import flash.utils.IDataOutput;
34 import flash.utils.ByteArray;
35 import flash.net.Socket;
36 import flash.events.EventDispatcher;
37
38
39 /**
40 * HTTP implementation of the TTransport interface. Used for working with a
41 * Thrift web services implementation.
42 * Unlike Http Client, it uses a single POST, and chunk-encoding to transfer all messages.
43 */
44
45 public class TFullDuplexHttpClient extends TTransport
46 {
47 private var socket:Socket = null;
48
49 private var host:String;
50
51 private var port:int;
52
53 private var resource:String;
54
55 private var stripped:Boolean = false;
56
57 private var obuffer:ByteArray = new ByteArray();
58
59 private var input:IDataInput;
60
61 private var output:IDataOutput;
62
63 private var bytesInChunk:int = 0;
64
65 private var CRLF:ByteArray = new ByteArray();
66
67 private var ioCallback:Function = null;
68
69 private var eventDispatcher:EventDispatcher = new EventDispatcher();
70
71 public function TFullDuplexHttpClient(host:String, port:int, resource:String):void
72 {
73 CRLF.writeByte(13);
74 CRLF.writeByte(10);
75 this.host = host;
76 this.port = port;
77 this.resource = resource;
78 }
79
80 public override function close():void
81 {
82 this.input = null;
83 this.output = null;
84 this.stripped = false;
85 socket.close()
86 }
87
88 public override function peek():Boolean
89 {
90 if(socket.connected)
91 {
92 trace("Bytes remained:" + socket.bytesAvailable);
93 return socket.bytesAvailable>0;
94 }
95 return false;
96 }
97
98 public override function read(buf:ByteArray, off:int, len:int):int
99 {
100 var n1:int = 0, n2:int = 0, n3:int = 0, n4:int = 0, cidx:int = 2;
101 var chunkSize:ByteArray = new ByteArray();
102
103 try
104 {
105 while (!stripped)
106 {
107 n1 = n2;
108 n2 = n3;
109 n3 = n4;
110 n4 = input.readByte();
111 if ((n1 == 13) && (n2 == 10) && (n3 == 13) && (n4 == 10))
112 {
113 stripped = true;
114 }
115 }
116
117 // read chunk size
118 if (bytesInChunk == 0)
119 {
120 n1 = input.readByte();
121 n2 = input.readByte();
122
123 chunkSize.writeByte(n1);
124 chunkSize.writeByte(n2);
125
126 while (!((n1 == 13) && (n2 == 10)))
127 {
128 n1 = n2;
129 n2 = input.readByte();
130 chunkSize.writeByte(n2);
131 }
132
133 bytesInChunk = parseInt(chunkSize.toString(), 16);
134 }
135
136 input.readBytes(buf, off, len);
137 debugBuffer(buf);
138 bytesInChunk -= len;
139
140 if (bytesInChunk == 0)
141 {
142 // advance the : "\r\n"
143 input.readUTFBytes(2);
144 }
145 return len;
146 }
147 catch (e:EOFError)
148 {
149 trace(e);
150 throw new TTransportError(TTransportError.UNKNOWN, "No more data available.");
151 }
152 catch (e:Error)
153 {
154 trace(e);
155 // WTF??
156 throw new TTransportError(TTransportError.UNKNOWN, "Bad IO error:" + e);
157 }
158 return 0;
159 }
160
161 public function debugBuffer(buf:ByteArray):void
162 {
163 var debug:String = "BUFFER >>";
164 var i:int;
165 for (i = 0; i < buf.length; i++)
166 {
167 debug += buf[i] as int;
168 debug += " ";
169 }
170
171 trace(debug + "<<");
172 }
173
174 public override function write(buf:ByteArray, off:int, len:int):void
175 {
176 obuffer.writeBytes(buf, off, len);
177 }
178
179 public function addEventListener(type:String, listener:Function, useCapture:Boolean = false, priority:int = 0, useWeakReference:Boolean = false):void
180 {
181 this.eventDispatcher.addEventListener(type, listener, useCapture, priority, useWeakReference);
182 }
183
184 public override function open():void
185 {
186 this.socket = new Socket();
187 this.socket.addEventListener(Event.CONNECT, socketConnected);
188 this.socket.addEventListener(IOErrorEvent.IO_ERROR, socketError);
189 this.socket.addEventListener(SecurityErrorEvent.SECURITY_ERROR, socketSecurityError);
190 this.socket.addEventListener(ProgressEvent.SOCKET_DATA, socketDataHandler);
191 this.socket.connect(host, port);
192 }
193
194 public function socketConnected(event:Event):void
195 {
196 this.output = this.socket;
197 this.input = this.socket;
198 this.output.writeUTF("CONNECT " + resource + " HTTP/1.1\n" + "Host: " + host + ":" + port + "\r\n" + "User-Agent: Thrift/AS3\r\n" + "Transfer-Encoding: chunked\r\n" + "content-type: application/x-thrift\r\n" + "Accept: */*\r\n\r\n");
199 this.eventDispatcher.dispatchEvent(event);
200 }
201
202 public function socketError(event:IOErrorEvent):void
203 {
204 trace("Error Connecting:" + event);
205 this.close();
206 if (ioCallback == null)
207 {
208 return;
209 }
210 ioCallback(new TTransportError(TTransportError.UNKNOWN, "IOError: " + event.text));
211 this.eventDispatcher.dispatchEvent(event);
212 }
213
214 public function socketSecurityError(event:SecurityErrorEvent):void
215 {
216 trace("Security Error Connecting:" + event);
217 this.close();
218 this.eventDispatcher.dispatchEvent(event);
219 }
220
221 public function socketDataHandler(event:ProgressEvent):void
222 {
223 trace("Got Data call:" +ioCallback);
224 if (ioCallback != null)
225 {
226 ioCallback(null);
227 };
228 this.eventDispatcher.dispatchEvent(event);
229 }
230
231 public override function flush(callback:Function = null):void
232 {
233 trace("set callback:" + callback);
234 this.ioCallback = callback;
235 this.output.writeUTF(this.obuffer.length.toString(16));
236 this.output.writeBytes(CRLF);
237 this.output.writeBytes(this.obuffer);
238 this.output.writeBytes(CRLF);
239 this.socket.flush();
240 // waiting for new Flex sdk 3.5
241 //this.obuffer.clear();
242 this.obuffer = new ByteArray();
243 }
244
245 public override function isOpen():Boolean
246 {
247 return (this.socket == null ? false : this.socket.connected);
248 }
249
250 }
251}