Refactor
:my
=>
'code'
Codes
Refactorings
Popular
Best
Submit
Spam
Account
Logout
Login
JavaScript doesn't seem to be activated, expect things to be ugly and sloppy!
More Jobs
Recent
Closure scoping issue
Parse HTTP Accept headers
Int32 Quick Parser
Find the file with the highest mtime in a directory
While loop to get unique value
ruby metaprogramming
includes_all?
Expanding input list using jQuery
Streamline attaching onPaste behavior to fields
Which is more readable? Math.* or if (...)
Popular
Int32 Quick Parser
ruby metaprogramming
includes_all?
Find the file with the highest mtime in a directory
Parse HTTP Accept headers
While loop to get unique value
Closure scoping issue
Command Pattern from Head First Design Patterns book.
Which is more readable? Math.* or if (...)
Streamline attaching onPaste behavior to fields
Pastable version of
AJAX Chat Socket Server
<div style="overflow:auto;border:solid 1px #ccc;background:#000;color:#F8F8F8"> <div class="section"> <pre style="float:left;margin:0 10px;border-right:0;color:#666;">1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400</pre> <pre class="sunburst"><span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span>!/usr/bin/env ruby</span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span> Simple Ruby XML Socket Server</span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span></span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span> This is a a simple socket server implementation in ruby</span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span> to communicate with flash clients via Flash XML Sockets.</span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span> </span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span> The socket code is based on the tutorial</span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span> "Sockets programming in Ruby"</span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span> by M. Tim Jones (mtj@mtjones.com).</span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span></span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span> Date:: Tue, 05 Mar 2008</span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span> Author:: Sebastian Tschan, https://blueimp.net</span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span> License:: GNU Affero General Public License</span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span> Include socket library:</span> <span style="color:#E28964;">require</span> <span style="color:#65B042;"><span style="color:#65B042;">'</span>socket<span style="color:#65B042;">'</span></span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span> Include XML libraries:</span> <span style="color:#E28964;">require</span> <span style="color:#65B042;"><span style="color:#65B042;">'</span>rexml/document<span style="color:#65B042;">'</span></span> <span style="color:#E28964;">require</span> <span style="color:#65B042;"><span style="color:#65B042;">'</span>rexml/streamlistener<span style="color:#65B042;">'</span></span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span> XML Stream Handler class used to parse chat messages:</span> <span style="color:#E28964;">class</span> <span style="text-decoration:underline;">XMLStreamHandler</span> <span style="color:#E28964;">attr_reader</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>type</span>,<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>chat_id</span>,<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>user_id</span>,<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>reg_id</span>,<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>channel_id</span>,<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>channel_ids</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Called when an opening tag (including attributes) is parsed:</span> <span style="color:#E28964;">def</span> <span style="color:#89BDFF;">tag_start</span> name, attrs <span style="color:#E28964;">case</span> name <span style="color:#E28964;">when</span> <span style="color:#65B042;"><span style="color:#65B042;">'</span>root<span style="color:#65B042;">'</span></span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> root messages are broadcast messages:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>type</span> <span style="color:#E28964;">=</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>message</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chat_id</span> <span style="color:#E28964;">=</span> attrs[<span style="color:#65B042;"><span style="color:#65B042;">'</span>chatID<span style="color:#65B042;">'</span></span>] <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>channel_id</span> <span style="color:#E28964;">=</span> attrs[<span style="color:#65B042;"><span style="color:#65B042;">'</span>channelID<span style="color:#65B042;">'</span></span>] <span style="color:#E28964;">throw</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>break</span> <span style="color:#E28964;">when</span> <span style="color:#65B042;"><span style="color:#65B042;">'</span>register<span style="color:#65B042;">'</span></span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> register messages are sent by chat clients:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>type</span> <span style="color:#E28964;">=</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>register</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chat_id</span> <span style="color:#E28964;">=</span> attrs[<span style="color:#65B042;"><span style="color:#65B042;">'</span>chatID<span style="color:#65B042;">'</span></span>] <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>user_id</span> <span style="color:#E28964;">=</span> attrs[<span style="color:#65B042;"><span style="color:#65B042;">'</span>userID<span style="color:#65B042;">'</span></span>] <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>reg_id</span> <span style="color:#E28964;">=</span> attrs[<span style="color:#65B042;"><span style="color:#65B042;">'</span>regID<span style="color:#65B042;">'</span></span>] <span style="color:#E28964;">throw</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>break</span> <span style="color:#E28964;">when</span> <span style="color:#65B042;"><span style="color:#65B042;">'</span>authenticate<span style="color:#65B042;">'</span></span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> authenticate messages are sent by the chat server client:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>type</span> <span style="color:#E28964;">=</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>authenticate</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chat_id</span> <span style="color:#E28964;">=</span> attrs[<span style="color:#65B042;"><span style="color:#65B042;">'</span>chatID<span style="color:#65B042;">'</span></span>] <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>user_id</span> <span style="color:#E28964;">=</span> attrs[<span style="color:#65B042;"><span style="color:#65B042;">'</span>userID<span style="color:#65B042;">'</span></span>] <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>reg_id</span> <span style="color:#E28964;">=</span> attrs[<span style="color:#65B042;"><span style="color:#65B042;">'</span>regID<span style="color:#65B042;">'</span></span>] <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>channel_ids</span> <span style="color:#E28964;">=</span> <span style="color:#9B859D;">Array</span>::<span style="color:#89BDFF;">new</span> <span style="color:#E28964;">when</span> <span style="color:#65B042;"><span style="color:#65B042;">'</span>channel<span style="color:#65B042;">'</span></span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> authenticate messages contain channel tags:</span> <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>channel_ids</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>channel_ids</span>.<span style="color:#89BDFF;">push</span>(attrs[<span style="color:#65B042;"><span style="color:#65B042;">'</span>id<span style="color:#65B042;">'</span></span>]) <span style="color:#E28964;">else</span> <span style="color:#E28964;">throw</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>break</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">when</span> <span style="color:#65B042;"><span style="color:#65B042;">'</span>policy-file-request<span style="color:#65B042;">'</span></span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> policy-file-requests are sent by flash clients for cross-domain authentication:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>type</span> <span style="color:#E28964;">=</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>policy_file_request</span> <span style="color:#E28964;">throw</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>break</span> <span style="color:#E28964;">else</span> <span style="color:#E28964;">throw</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>break</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Called when a closing tag is parsed:</span> <span style="color:#E28964;">def</span> <span style="color:#89BDFF;">tag_end</span> name <span style="color:#E28964;">if</span> name <span style="color:#E28964;">==</span> <span style="color:#65B042;"><span style="color:#65B042;">'</span>authenticate<span style="color:#65B042;">'</span></span> <span style="color:#E28964;">throw</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>break</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">def</span> <span style="color:#89BDFF;">text</span> text <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Called on text between tags</span> <span style="color:#E28964;">end</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Called when cdata is parsed:</span> <span style="color:#E28964;">alias</span> cdata text <span style="color:#E28964;">end</span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span> Socket Server class:</span> <span style="color:#E28964;">class</span> <span style="text-decoration:underline;">SocketServer</span> <span style="color:#E28964;">def</span> <span style="color:#89BDFF;">initialize</span>(<span style="color:#3E87E3;">config_file</span>) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> List of configuration settings:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span> <span style="color:#E28964;">=</span> <span style="color:#9B859D;">Hash</span>::<span style="color:#89BDFF;">new</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Initialize default settings:</span> initialize_default_properties <span style="color:#E28964;">if</span> config_file <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Load settings from configuration file:</span> <span style="color:#89BDFF;">load_properties_from_file</span>(config_file) <span style="color:#E28964;">end</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Sockets list:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>sockets</span> <span style="color:#E28964;">=</span> <span style="color:#9B859D;">Array</span>::<span style="color:#89BDFF;">new</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Clients list:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>clients</span> <span style="color:#E28964;">=</span> <span style="color:#9B859D;">Hash</span>::<span style="color:#89BDFF;">new</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Chats list, used to distinguish between different chat installations (contains channels list):</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span> <span style="color:#E28964;">=</span> <span style="color:#9B859D;">Hash</span>::<span style="color:#89BDFF;">new</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Initialize server socket:</span> initialize_server_socket <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>server_socket</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Log server start (STDOUT.flush prevents output buffering):</span> puts <span style="color:#65B042;"><span style="color:#65B042;">"</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#9B859D;">Time</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">now</span></span><span style="color:#DAEFA3;">}</span></span><span style="color:#DDF2A4;">\t</span>Server started on Port <span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#8A9A95;"><span style="color:#8A9A95;">@</span>config</span><span style="color:#DAEFA3;">[</span><span style="color:#DDF2A4;"><span style="color:#DDF2A4;">:</span>server_port</span><span style="color:#DAEFA3;">]</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">to_s</span></span><span style="color:#DAEFA3;">}</span></span> ...<span style="color:#65B042;">"</span></span>; <span style="color:#3E87E3;">STDOUT</span>.<span style="color:#89BDFF;">flush</span> <span style="color:#E28964;">begin</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Start the server:</span> run <span style="color:#E28964;">rescue</span> <span style="color:#3E87E3;">SignalException</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Controlled stop:</span> <span style="color:#E28964;">ensure</span> <span style="color:#E28964;">for</span> socket <span style="color:#E28964;">in</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>sockets</span> <span style="color:#E28964;">if</span> socket <span style="color:#E28964;">!=</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>server_socket</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Disconnect all clients:</span> <span style="color:#89BDFF;">handle_client_disconnection</span>(socket, <span style="color:#3387CC;">false</span>) <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>sockets</span> <span style="color:#E28964;">=</span> <span style="color:#3387CC;">nil</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>clients</span> <span style="color:#E28964;">=</span> <span style="color:#3387CC;">nil</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Log server stop:</span> puts <span style="color:#65B042;"><span style="color:#65B042;">"</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#9B859D;">Time</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">now</span></span><span style="color:#DAEFA3;">}</span></span><span style="color:#DDF2A4;">\t</span>Server stopped.<span style="color:#65B042;">"</span></span>; <span style="color:#3E87E3;">STDOUT</span>.<span style="color:#89BDFF;">flush</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">def</span> <span style="color:#89BDFF;">run</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Endless loop:</span> <span style="color:#E28964;">while</span> <span style="color:#3387CC;">1</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Blocking select call. The first three parameters are arrays of IO objects or nil.</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> The last parameter is to set a timeout in seconds to force select to return</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> if no event has occurred on any of the given IO object arrays.</span> res <span style="color:#E28964;">=</span> <span style="color:#89BDFF;">select</span>(<span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>sockets</span>, <span style="color:#3387CC;">nil</span>, <span style="color:#3387CC;">nil</span>, <span style="color:#3387CC;">nil</span>) <span style="color:#E28964;">if</span> res <span style="color:#E28964;">!=</span> <span style="color:#3387CC;">nil</span> <span style="color:#E28964;">then</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Iterate through the tagged read descriptors:</span> <span style="color:#E28964;">for</span> socket <span style="color:#E28964;">in</span> res[<span style="color:#3387CC;">0</span>] <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Received a connect to the server socket:</span> <span style="color:#E28964;">if</span> socket <span style="color:#E28964;">==</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>server_socket</span> <span style="color:#E28964;">then</span> accept_new_connection <span style="color:#E28964;">else</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Received something on a client socket:</span> <span style="color:#E28964;">if</span> socket.<span style="color:#89BDFF;">eof?</span> <span style="color:#E28964;">then</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Handle client disconnection:</span> <span style="color:#89BDFF;">handle_client_disconnection</span>(socket) <span style="color:#E28964;">else</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Handle client input data:</span> <span style="color:#89BDFF;">handle_client_input</span>(socket, socket.<span style="color:#89BDFF;">gets</span>(<span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>eol</span>])) <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">private</span> <span style="color:#E28964;">def</span> <span style="color:#89BDFF;">initialize_default_properties</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Server address (empty = bind to all available interfaces):</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>server_address</span>] <span style="color:#E28964;">=</span> <span style="color:#65B042;"><span style="color:#65B042;">'</span><span style="color:#65B042;">'</span></span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Server port:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>server_port</span>] <span style="color:#E28964;">=</span> <span style="color:#3387CC;">1935</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Comma-separated list of clients allowed to broadcast (allows all if empty):</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>broadcast_clients</span>] <span style="color:#E28964;">=</span> <span style="color:#65B042;"><span style="color:#65B042;">'</span><span style="color:#65B042;">'</span></span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Defines if broadcast is sent to broadcasting client:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>broadcast_self</span>] <span style="color:#E28964;">=</span> <span style="color:#3387CC;">false</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Maximum number of clients (0 allows an unlimited number of clients):</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>max_clients</span>] <span style="color:#E28964;">=</span> <span style="color:#3387CC;">0</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Comma-separated list of domains from which downloaded Flash clients are allowed to connect (* allows all domains):</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>allow_access_from</span>] <span style="color:#E28964;">=</span> <span style="color:#65B042;"><span style="color:#65B042;">'</span>*<span style="color:#65B042;">'</span></span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Defines the cross-domain-policy string sent to Flash clients as response to a policy-file-request:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>cross_domain_policy</span>] <span style="color:#E28964;">=</span> <span style="color:#65B042;"><span style="color:#65B042;">'</span><cross-domain-policy><allow-access-from domain="<span style="color:#65B042;">'</span></span><span style="color:#E28964;">+@</span>config[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>allow_access_from</span>]<span style="color:#E28964;">+</span><span style="color:#65B042;"><span style="color:#65B042;">'</span>" to-ports="<span style="color:#65B042;">'</span></span><span style="color:#E28964;">+@</span>config[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>server_port</span>].<span style="color:#89BDFF;">to_s</span><span style="color:#E28964;">+</span><span style="color:#65B042;"><span style="color:#65B042;">'</span>"/></cross-domain-policy><span style="color:#65B042;">'</span></span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> EOL (End Of Line) character used by Flash XML Socket communication (a null-byte):</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>eol</span>] <span style="color:#E28964;">=</span> <span style="color:#65B042;"><span style="color:#65B042;">"</span><span style="color:#DDF2A4;">\0</span><span style="color:#65B042;">"</span></span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Log level (0 logs only errors and server start/stop, 1 logs client connections, 2 logs all messages but no broadcast content, 3 logs everything):</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>log_level</span>] <span style="color:#E28964;">=</span> <span style="color:#3387CC;">0</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">def</span> <span style="color:#89BDFF;">load_properties_from_file</span>(<span style="color:#3E87E3;">config_file</span>) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Open the config file and go through each line:</span> <span style="color:#9B859D;">File</span>.<span style="color:#89BDFF;">open</span>(config_file, <span style="color:#65B042;"><span style="color:#65B042;">'</span>r<span style="color:#65B042;">'</span></span>) <span style="color:#E28964;">do </span>|<span style="color:#3E87E3;">file</span>| file.<span style="color:#89BDFF;">read</span>.<span style="color:#89BDFF;">each_line</span> <span style="color:#E28964;">do </span>|<span style="color:#3E87E3;">line</span>| <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Remove trailing whitespace from the line:</span> line.<span style="color:#89BDFF;">strip!</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Get the position of the first "=":</span> i <span style="color:#E28964;">=</span> line.<span style="color:#89BDFF;">index</span>(<span style="color:#65B042;"><span style="color:#65B042;">'</span>=<span style="color:#65B042;">'</span></span>) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Check if line is not a comment and a valid property:</span> <span style="color:#E28964;">if</span> (!line.<span style="color:#89BDFF;">empty?</span> <span style="color:#E28964;">&&</span> line[<span style="color:#3387CC;">0</span>] <span style="color:#E28964;">!=</span> <span style="color:#3387CC;">?#</span> <span style="color:#E28964;">&&</span> i <span style="color:#E28964;">></span> <span style="color:#3387CC;">0</span>) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Add the configuration option to the config hash:</span> key <span style="color:#E28964;">=</span> line[<span style="color:#3387CC;">0</span>..i <span style="color:#E28964;">-</span> <span style="color:#3387CC;">1</span>].<span style="color:#89BDFF;">strip</span> value <span style="color:#E28964;">=</span> line[i <span style="color:#E28964;">+</span> <span style="color:#3387CC;">1</span>..<span style="color:#E28964;">-</span><span style="color:#3387CC;">1</span>].<span style="color:#89BDFF;">strip</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Parse boolean values:</span> <span style="color:#E28964;">if</span> value.<span style="color:#89BDFF;">eql?</span>(<span style="color:#65B042;"><span style="color:#65B042;">'</span>false<span style="color:#65B042;">'</span></span>) <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[key.<span style="color:#89BDFF;">to_sym</span>] <span style="color:#E28964;">=</span> <span style="color:#3387CC;">false</span> <span style="color:#E28964;">elsif</span> value.<span style="color:#89BDFF;">eql?</span>(<span style="color:#65B042;"><span style="color:#65B042;">'</span>true<span style="color:#65B042;">'</span></span>) <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[key.<span style="color:#89BDFF;">to_sym</span>] <span style="color:#E28964;">=</span> <span style="color:#3387CC;">true</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Parse integer numbers:</span> <span style="color:#E28964;">elsif</span> value.<span style="color:#89BDFF;">to_i</span>.<span style="color:#89BDFF;">to_s</span>.<span style="color:#89BDFF;">eql?</span>(value) <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[key.<span style="color:#89BDFF;">to_sym</span>] <span style="color:#E28964;">=</span> value.<span style="color:#89BDFF;">to_i</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Parse floating point numbers:</span> <span style="color:#E28964;">elsif</span> value.<span style="color:#89BDFF;">to_f</span>.<span style="color:#89BDFF;">to_s</span>.<span style="color:#89BDFF;">eql?</span>(value) <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[key.<span style="color:#89BDFF;">to_sym</span>] <span style="color:#E28964;">=</span> value.<span style="color:#89BDFF;">to_f</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Parse string values:</span> <span style="color:#E28964;">else</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[key.<span style="color:#89BDFF;">to_sym</span>] <span style="color:#E28964;">=</span> value <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>eol</span>].<span style="color:#89BDFF;">empty?</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Use default EOL if configuration option is empty:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>eol</span>] <span style="color:#E28964;">=</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">$</span>/</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">def</span> <span style="color:#89BDFF;">initialize_server_socket</span> <span style="color:#E28964;">begin</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> The server socket, allowing connections from any interface and bound to the given port number:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>server_socket</span> <span style="color:#E28964;">=</span> <span style="color:#3E87E3;">TCPServer</span>.<span style="color:#89BDFF;">new</span>(<span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>server_address</span>], <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>server_port</span>].<span style="color:#89BDFF;">to_i</span>) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Enable reuse of the server address (e.g. for rapid restarts of the server):</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>server_socket</span>.<span style="color:#89BDFF;">setsockopt</span>(<span style="color:#9B859D;">Socket</span>::<span style="color:#89BDFF;">SOL_SOCKET</span>, <span style="color:#9B859D;">Socket</span>::<span style="color:#89BDFF;">SO_REUSEADDR</span>, <span style="color:#3387CC;">1</span>) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Add the server socket to the sockets list:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>sockets</span>.<span style="color:#89BDFF;">push</span>(<span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>server_socket</span>) <span style="color:#E28964;">rescue</span> <span style="color:#3E87E3;">Exception</span> => error <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Log initialization failure:</span> puts <span style="color:#65B042;"><span style="color:#65B042;">"</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#9B859D;">Time</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">now</span></span><span style="color:#DAEFA3;">}</span></span><span style="color:#DDF2A4;">\t</span>Failed to initialize Server on Port <span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#8A9A95;"><span style="color:#8A9A95;">@</span>config</span><span style="color:#DAEFA3;">[</span><span style="color:#DDF2A4;"><span style="color:#DDF2A4;">:</span>server_port</span><span style="color:#DAEFA3;">]</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">to_s</span></span><span style="color:#DAEFA3;">}</span></span>: <span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>error<span style="color:#DAEFA3;">}</span></span>.<span style="color:#65B042;">"</span></span>; <span style="color:#3E87E3;">STDOUT</span>.<span style="color:#89BDFF;">flush</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">def</span> <span style="color:#89BDFF;">accept_new_connection</span> <span style="color:#E28964;">begin</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Accept the client connection:</span> socket <span style="color:#E28964;">=</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>server_socket</span>.<span style="color:#89BDFF;">accept</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Retrieve IP and Port:</span> ip <span style="color:#E28964;">=</span> socket.<span style="color:#89BDFF;">peeraddr</span>[<span style="color:#3387CC;">3</span>] port <span style="color:#E28964;">=</span> socket.<span style="color:#89BDFF;">peeraddr</span>[<span style="color:#3387CC;">1</span>] <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Check if we have reached the maximum number of connected clients (always accept the broadcast clients):</span> <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>max_clients</span>].<span style="color:#89BDFF;">to_i</span> <span style="color:#E28964;">==</span> <span style="color:#3387CC;">0</span> <span style="color:#E28964;">||</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>clients</span>.<span style="color:#89BDFF;">size</span> <span style="color:#E28964;"><</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>max_clients</span>].<span style="color:#89BDFF;">to_i</span> <span style="color:#E28964;">||</span> <span style="color:#E28964;">!</span><span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>broadcast_clients</span>].<span style="color:#89BDFF;">empty?</span> <span style="color:#E28964;">&&</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>broadcast_clients</span>].<span style="color:#89BDFF;">include?</span>(ip) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Add the accepted socket connection to the socket list:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>sockets</span>.<span style="color:#89BDFF;">push</span>(socket) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Create a new Hash to store the client data:</span> client <span style="color:#E28964;">=</span> <span style="color:#9B859D;">Hash</span>::<span style="color:#89BDFF;">new</span> client[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>id</span>] <span style="color:#E28964;">=</span> <span style="color:#65B042;"><span style="color:#65B042;">"</span>[<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>ip<span style="color:#DAEFA3;">}</span></span>]:<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>port<span style="color:#DAEFA3;">}</span></span><span style="color:#65B042;">"</span></span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Check if the client is allowed to broadcast:</span> <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>broadcast_clients</span>].<span style="color:#89BDFF;">empty?</span> <span style="color:#E28964;">||</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>broadcast_clients</span>].<span style="color:#89BDFF;">include?</span>(ip) client[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>allowed_to_broadcast</span>] <span style="color:#E28964;">=</span> <span style="color:#3387CC;">true</span> <span style="color:#E28964;">else</span> client[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>allowed_to_broadcast</span>] <span style="color:#E28964;">=</span> <span style="color:#3387CC;">false</span> <span style="color:#E28964;">end</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Add the client to the clients list: </span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>clients</span>[socket] <span style="color:#E28964;">=</span> client <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>log_level</span>].<span style="color:#89BDFF;">to_i</span> <span style="color:#E28964;">></span> <span style="color:#3387CC;">0</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Log client connection and the number of connected clients:</span> puts <span style="color:#65B042;"><span style="color:#65B042;">"</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#9B859D;">Time</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">now</span></span><span style="color:#DAEFA3;">}</span></span><span style="color:#DDF2A4;">\t</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>client<span style="color:#DAEFA3;">[</span><span style="color:#DDF2A4;"><span style="color:#DDF2A4;">:</span>id</span><span style="color:#DAEFA3;">]</span><span style="color:#DAEFA3;">}</span></span> Connects<span style="color:#DDF2A4;">\t</span>(<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#8A9A95;"><span style="color:#8A9A95;">@</span>clients</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">size</span></span><span style="color:#DAEFA3;">}</span></span> connected)<span style="color:#65B042;">"</span></span>; <span style="color:#3E87E3;">STDOUT</span>.<span style="color:#89BDFF;">flush</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">else</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Close the socket connection:</span> socket.<span style="color:#89BDFF;">close</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">rescue</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Client disconnected before the address information (IP, Port) could be retrieved.</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">def</span> <span style="color:#89BDFF;">handle_client_disconnection</span>(<span style="color:#3E87E3;">client_socket<span style="color:#3E87E3;">,</span> delete_socket<span style="color:#E28964;">=</span><span style="color:#3387CC;">true</span></span>) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Retrieve the client ID for the current socket:</span> client_id <span style="color:#E28964;">=</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>clients</span>[client_socket][<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>id</span>] <span style="color:#E28964;">begin</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Close the socket connection:</span> client_socket.<span style="color:#89BDFF;">close</span> <span style="color:#E28964;">rescue</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Rescue if closing the socket fails</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">if</span> delete_socket <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Remove the socket from the sockets list:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>sockets</span>.<span style="color:#89BDFF;">delete</span>(client_socket) <span style="color:#E28964;">end</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Remove the client ID from the clients list:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>clients</span>.<span style="color:#89BDFF;">delete</span>(client_socket) <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>log_level</span>].<span style="color:#89BDFF;">to_i</span> <span style="color:#E28964;">></span> <span style="color:#3387CC;">0</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Log client disconnection and the number of connected clients:</span> puts <span style="color:#65B042;"><span style="color:#65B042;">"</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#9B859D;">Time</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">now</span></span><span style="color:#DAEFA3;">}</span></span><span style="color:#DDF2A4;">\t</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>client_id<span style="color:#DAEFA3;">}</span></span> Disconnects<span style="color:#DDF2A4;">\t</span>(<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#8A9A95;"><span style="color:#8A9A95;">@</span>clients</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">size</span></span><span style="color:#DAEFA3;">}</span></span> connected)<span style="color:#65B042;">"</span></span>; <span style="color:#3E87E3;">STDOUT</span>.<span style="color:#89BDFF;">flush</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">def</span> <span style="color:#89BDFF;">handle_client_input</span>(<span style="color:#3E87E3;">client_socket<span style="color:#3E87E3;">,</span> str</span>) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Create a new XML stream handler:</span> handler <span style="color:#E28964;">=</span> <span style="color:#3E87E3;">XMLStreamHandler</span>.<span style="color:#89BDFF;">new</span> <span style="color:#E28964;">begin</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> As soon as the parser has found the relevant information it throws a :break symbol:</span> <span style="color:#E28964;">catch</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>break</span> <span style="color:#E28964;">do</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Parse the given input string for XML messages:</span> <span style="color:#3E87E3;">REXML</span>::<span style="color:#89BDFF;">Document</span>.<span style="color:#89BDFF;">parse_stream</span>(str, handler) <span style="color:#E28964;">end</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> The handler stores a type property to define the parsed XML message:</span> <span style="color:#E28964;">case</span> handler.<span style="color:#89BDFF;">type</span> <span style="color:#E28964;">when</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>message</span> <span style="color:#89BDFF;">handle_broadcast_message</span>(client_socket, handler.<span style="color:#89BDFF;">chat_id</span>, handler.<span style="color:#89BDFF;">channel_id</span>, str) <span style="color:#E28964;">when</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>register</span> <span style="color:#89BDFF;">handle_client_registration</span>(client_socket, handler.<span style="color:#89BDFF;">chat_id</span>, handler.<span style="color:#89BDFF;">user_id</span>, handler.<span style="color:#89BDFF;">reg_id</span>) <span style="color:#E28964;">when</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>authenticate</span> <span style="color:#89BDFF;">handle_client_authentication</span>(client_socket, handler.<span style="color:#89BDFF;">chat_id</span>, handler.<span style="color:#89BDFF;">user_id</span>, handler.<span style="color:#89BDFF;">reg_id</span>, handler.<span style="color:#89BDFF;">channel_ids</span>) <span style="color:#E28964;">when</span> <span style="color:#3387CC;"><span style="color:#3387CC;">:</span>policy_file_request</span> <span style="color:#89BDFF;">handle_policy_file_request</span>(client_socket) <span style="color:#E28964;">end</span> <span style="color:#E28964;">rescue</span> <span style="color:#3E87E3;">Exception</span> => error <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Rescue if parsing the client input fails and log the error message:</span> puts <span style="color:#65B042;"><span style="color:#65B042;">"</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#9B859D;">Time</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">now</span></span><span style="color:#DAEFA3;">}</span></span><span style="color:#DDF2A4;">\t</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#8A9A95;"><span style="color:#8A9A95;">@</span>clients</span><span style="color:#DAEFA3;">[</span>client_socket<span style="color:#DAEFA3;">]</span><span style="color:#DAEFA3;">[</span><span style="color:#DDF2A4;"><span style="color:#DDF2A4;">:</span>id</span><span style="color:#DAEFA3;">]</span><span style="color:#DAEFA3;">}</span></span> Client Input Error:<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>error<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">to_s</span></span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">dump</span></span><span style="color:#DAEFA3;">}</span></span><span style="color:#65B042;">"</span></span>; <span style="color:#3E87E3;">STDOUT</span>.<span style="color:#89BDFF;">flush</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">def</span> <span style="color:#89BDFF;">handle_broadcast_message</span>(<span style="color:#3E87E3;">client_socket<span style="color:#3E87E3;">,</span> chat_id<span style="color:#3E87E3;">,</span> channel_id<span style="color:#3E87E3;">,</span> str</span>) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Check if the_client is allowed to broadcast:</span> <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>clients</span>[client_socket][<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>allowed_to_broadcast</span>] <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Check if the chat and channel have been registered:</span> <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id] <span style="color:#E28964;">&&</span> (<span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id][channel_id] <span style="color:#E28964;">||</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id][<span style="color:#65B042;"><span style="color:#65B042;">'</span>ALL<span style="color:#65B042;">'</span></span>]) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Go through the sockets list:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>sockets</span>.<span style="color:#89BDFF;">each</span> <span style="color:#E28964;">do </span>|<span style="color:#3E87E3;">socket</span>| <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Skip the server socket and skip the the client socket if broadcast is not to be sent to self:</span> <span style="color:#E28964;">if</span> socket <span style="color:#E28964;">!=</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>server_socket</span> <span style="color:#E28964;">&&</span> (<span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>broadcast_self</span>] <span style="color:#E28964;">||</span> socket <span style="color:#E28964;">!=</span> client_socket) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Only write to clients registered to the given channel or to the "ALL" channel:</span> <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id][<span style="color:#65B042;"><span style="color:#65B042;">'</span>ALL<span style="color:#65B042;">'</span></span>] reg_id <span style="color:#E28964;">=</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id][<span style="color:#65B042;"><span style="color:#65B042;">'</span>ALL<span style="color:#65B042;">'</span></span>][<span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>clients</span>[socket][<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>user_id</span>]] <span style="color:#E28964;">end</span> <span style="color:#E28964;">if</span> <span style="color:#E28964;">!</span>reg_id <span style="color:#E28964;">&&</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id][channel_id] reg_id <span style="color:#E28964;">=</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id][channel_id][<span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>clients</span>[socket][<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>user_id</span>]] <span style="color:#E28964;">end</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Check if the reg_id stored for the given channel and user_id matches the clients reg_id:</span> <span style="color:#E28964;">if</span> reg_id <span style="color:#E28964;">&&</span> reg_id.<span style="color:#89BDFF;">eql?</span>(<span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>clients</span>[socket][<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>reg_id</span>]) <span style="color:#E28964;">begin</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Write the broadcast message on the socket connection:</span> socket.<span style="color:#89BDFF;">write</span>(str) <span style="color:#E28964;">rescue</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Rescue if writing to the socket fails</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>log_level</span>].<span style="color:#89BDFF;">to_i</span> <span style="color:#E28964;">></span> <span style="color:#3387CC;">2</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Log the message sent by the broadcast client:</span> puts <span style="color:#65B042;"><span style="color:#65B042;">"</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#9B859D;">Time</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">now</span></span><span style="color:#DAEFA3;">}</span></span><span style="color:#DDF2A4;">\t</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#8A9A95;"><span style="color:#8A9A95;">@</span>clients</span><span style="color:#DAEFA3;">[</span>client_socket<span style="color:#DAEFA3;">]</span><span style="color:#DAEFA3;">[</span><span style="color:#DDF2A4;"><span style="color:#DDF2A4;">:</span>id</span><span style="color:#DAEFA3;">]</span><span style="color:#DAEFA3;">}</span></span> Chat:<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>chat_id<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">to_s</span></span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">dump</span></span><span style="color:#DAEFA3;">}</span></span> Channel:<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>channel_id<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">to_s</span></span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">dump</span></span><span style="color:#DAEFA3;">}</span></span> Message:<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>str<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">to_s</span></span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">dump</span></span><span style="color:#DAEFA3;">}</span></span><span style="color:#65B042;">"</span></span>; <span style="color:#3E87E3;">STDOUT</span>.<span style="color:#89BDFF;">flush</span> <span style="color:#E28964;">elsif</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>log_level</span>].<span style="color:#89BDFF;">to_i</span> <span style="color:#E28964;">></span> <span style="color:#3387CC;">1</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Log the message sent by the broadcast client:</span> puts <span style="color:#65B042;"><span style="color:#65B042;">"</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#9B859D;">Time</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">now</span></span><span style="color:#DAEFA3;">}</span></span><span style="color:#DDF2A4;">\t</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#8A9A95;"><span style="color:#8A9A95;">@</span>clients</span><span style="color:#DAEFA3;">[</span>client_socket<span style="color:#DAEFA3;">]</span><span style="color:#DAEFA3;">[</span><span style="color:#DDF2A4;"><span style="color:#DDF2A4;">:</span>id</span><span style="color:#DAEFA3;">]</span><span style="color:#DAEFA3;">}</span></span> Chat:<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>chat_id<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">to_s</span></span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">dump</span></span><span style="color:#DAEFA3;">}</span></span> Channel:<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>channel_id<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">to_s</span></span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">dump</span></span><span style="color:#DAEFA3;">}</span></span> Message<span style="color:#65B042;">"</span></span>; <span style="color:#3E87E3;">STDOUT</span>.<span style="color:#89BDFF;">flush</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">def</span> <span style="color:#89BDFF;">handle_client_registration</span>(<span style="color:#3E87E3;">client_socket<span style="color:#3E87E3;">,</span> chat_id<span style="color:#3E87E3;">,</span> user_id<span style="color:#3E87E3;">,</span> reg_id</span>) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Save the chat_id, use_id and reg_id as client properties:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>clients</span>[client_socket][<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>chat_id</span>] <span style="color:#E28964;">=</span> chat_id <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>clients</span>[client_socket][<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>user_id</span>] <span style="color:#E28964;">=</span> user_id <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>clients</span>[client_socket][<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>reg_id</span>] <span style="color:#E28964;">=</span> reg_id <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>log_level</span>].<span style="color:#89BDFF;">to_i</span> <span style="color:#E28964;">></span> <span style="color:#3387CC;">1</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Log the client registration:</span> puts <span style="color:#65B042;"><span style="color:#65B042;">"</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#9B859D;">Time</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">now</span></span><span style="color:#DAEFA3;">}</span></span><span style="color:#DDF2A4;">\t</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#8A9A95;"><span style="color:#8A9A95;">@</span>clients</span><span style="color:#DAEFA3;">[</span>client_socket<span style="color:#DAEFA3;">]</span><span style="color:#DAEFA3;">[</span><span style="color:#DDF2A4;"><span style="color:#DDF2A4;">:</span>id</span><span style="color:#DAEFA3;">]</span><span style="color:#DAEFA3;">}</span></span> Chat:<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>chat_id<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">to_s</span></span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">dump</span></span><span style="color:#DAEFA3;">}</span></span> User:<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>user_id<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">to_s</span></span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">dump</span></span><span style="color:#DAEFA3;">}</span></span> Reg:<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>reg_id<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">to_s</span></span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">dump</span></span><span style="color:#DAEFA3;">}</span></span><span style="color:#65B042;">"</span></span>; <span style="color:#3E87E3;">STDOUT</span>.<span style="color:#89BDFF;">flush</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">def</span> <span style="color:#89BDFF;">handle_client_authentication</span>(<span style="color:#3E87E3;">client_socket<span style="color:#3E87E3;">,</span> chat_id<span style="color:#3E87E3;">,</span> user_id<span style="color:#3E87E3;">,</span> reg_id<span style="color:#3E87E3;">,</span> channel_ids</span>) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Only the broadcast clients may send authentication messages:</span> <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>clients</span>[client_socket][<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>allowed_to_broadcast</span>] <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Create a new chat item if not found for the given chat_id:</span> <span style="color:#E28964;">if</span> <span style="color:#E28964;">!</span><span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id] <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id] <span style="color:#E28964;">=</span> <span style="color:#9B859D;">Hash</span>.<span style="color:#89BDFF;">new</span> <span style="color:#E28964;">end</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Go through the list of channels for the given chat:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id].<span style="color:#89BDFF;">each_key</span> <span style="color:#E28964;">do </span>|<span style="color:#3E87E3;">key</span>| <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Delete all items for the given user on all channels of the given chat:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id][key].<span style="color:#89BDFF;">delete</span>(user_id) <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> If the chat channel is empty, delete the channel item:</span> <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id][key].<span style="color:#89BDFF;">size</span> <span style="color:#E28964;">==</span> <span style="color:#3387CC;">0</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id].<span style="color:#89BDFF;">delete</span>(key) <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Go through the list of authenticated channel_ids:</span> channel_ids.<span style="color:#89BDFF;">each</span> <span style="color:#E28964;">do </span>|<span style="color:#3E87E3;">channel_id</span>| <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Create a new channel item if not found for the current channel_id (and the given chat_id):</span> <span style="color:#E28964;">if</span> <span style="color:#E28964;">!</span><span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id][channel_id] <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id][channel_id] <span style="color:#E28964;">=</span> <span style="color:#9B859D;">Hash</span>.<span style="color:#89BDFF;">new</span> <span style="color:#E28964;">end</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Add a user item of the given user_id with the given reg_id to the current channel:</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>chats</span>[chat_id][channel_id][user_id] <span style="color:#E28964;">=</span> reg_id <span style="color:#E28964;">end</span> <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>log_level</span>].<span style="color:#89BDFF;">to_i</span> <span style="color:#E28964;">></span> <span style="color:#3387CC;">1</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Log the client authentication:</span> puts <span style="color:#65B042;"><span style="color:#65B042;">"</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#9B859D;">Time</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">now</span></span><span style="color:#DAEFA3;">}</span></span><span style="color:#DDF2A4;">\t</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#8A9A95;"><span style="color:#8A9A95;">@</span>clients</span><span style="color:#DAEFA3;">[</span>client_socket<span style="color:#DAEFA3;">]</span><span style="color:#DAEFA3;">[</span><span style="color:#DDF2A4;"><span style="color:#DDF2A4;">:</span>id</span><span style="color:#DAEFA3;">]</span><span style="color:#DAEFA3;">}</span></span> Chat:<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>chat_id<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">to_s</span></span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">dump</span></span><span style="color:#DAEFA3;">}</span></span> User:<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>user_id<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">to_s</span></span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">dump</span></span><span style="color:#DAEFA3;">}</span></span> Auth:<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>reg_id<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">to_s</span></span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">dump</span></span><span style="color:#DAEFA3;">}</span></span> Channels:<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span>channel_ids<span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">join</span></span><span style="color:#DAEFA3;">(</span><span style="color:#65B042;"><span style="color:#65B042;">'</span>,<span style="color:#65B042;">'</span></span><span style="color:#DAEFA3;">)</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">dump</span></span><span style="color:#DAEFA3;">}</span></span><span style="color:#65B042;">"</span></span>; <span style="color:#3E87E3;">STDOUT</span>.<span style="color:#89BDFF;">flush</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">def</span> <span style="color:#89BDFF;">handle_policy_file_request</span>(<span style="color:#3E87E3;">client_socket</span>) <span style="color:#E28964;">begin</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Write the cross-domain-policy to the Flash client:</span> client_socket.<span style="color:#89BDFF;">write</span>(<span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>cross_domain_policy</span>]<span style="color:#E28964;">+@</span>config[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>eol</span>]) <span style="color:#E28964;">rescue</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Rescue if writing to the socket fails</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">if</span> <span style="color:#3E87E3;"><span style="color:#3E87E3;">@</span>config</span>[<span style="color:#3387CC;"><span style="color:#3387CC;">:</span>log_level</span>].<span style="color:#89BDFF;">to_i</span> <span style="color:#E28964;">></span> <span style="color:#3387CC;">1</span> <span style="color:#AEAEAE;font-style:italic;"> <span style="color:#AEAEAE;font-style:italic;">#</span> Log the policy-file-request:</span> puts <span style="color:#65B042;"><span style="color:#65B042;">"</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#9B859D;">Time</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">.</span><span style="color:#89BDFF;">now</span></span><span style="color:#DAEFA3;">}</span></span><span style="color:#DDF2A4;">\t</span><span style="color:#DAEFA3;"><span style="color:#DAEFA3;">#{</span><span style="color:#8A9A95;"><span style="color:#8A9A95;">@</span>clients</span><span style="color:#DAEFA3;">[</span>client_socket<span style="color:#DAEFA3;">]</span><span style="color:#DAEFA3;">[</span><span style="color:#DDF2A4;"><span style="color:#DDF2A4;">:</span>id</span><span style="color:#DAEFA3;">]</span><span style="color:#DAEFA3;">}</span></span> Policy-File-Request<span style="color:#65B042;">"</span></span>; <span style="color:#3E87E3;">STDOUT</span>.<span style="color:#89BDFF;">flush</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#E28964;">end</span> <span style="color:#AEAEAE;font-style:italic;"><span style="color:#AEAEAE;font-style:italic;">#</span> Start the socket server with the first command line argument as configuration file:</span> <span style="color:#9B859D;">SocketServer</span>.<span style="color:#89BDFF;">new</span>(<span style="color:#3E87E3;"><span style="color:#3E87E3;">$</span>*</span>[<span style="color:#3387CC;">0</span>]) </pre> </div> </div> <a href="http://refactormycode.com/codes/268-ajax-chat-socket-server" style="color:#fff" title="As seen on RefactorMyCode.com"><img alt="Small_logo" src="http://refactormycode.com/images/small_logo.gif" style="border:0" /></a>