Initial implementation of chat.

This commit is contained in:
Martin Edenhofer 2012-11-02 17:10:22 +01:00
parent f723ea3cdb
commit 06c4b25e7c
9 changed files with 80 additions and 12 deletions

View file

@ -86,7 +86,7 @@ class Index extends App.Controller
App[key].refresh( value, options: { clear: true } )
# rebuild navbar with user data
App.Event.trigger 'navrebuild', data.session
App.Event.trigger 'ajax:auth', data.session
# update websocked auth info
App.WebSocket.auth()

View file

@ -15,7 +15,7 @@ class Index extends Spine.Controller
@log 'Session', window.Session
window.Session = {}
@log 'Session', window.Session
App.Event.trigger 'navrebuild'
App.Event.trigger 'ajax:auth'
# redirect to login
@navigate 'login'

View file

@ -11,8 +11,8 @@ class App.Navigation extends App.Controller
@update(arguments[0])
# rebuild nav bar with given user data
App.Event.bind 'navrebuild', (user) =>
@log 'navbarrebuild', user
App.Event.bind 'ajax:auth', (user) =>
@log 'navbar rebuild', user
if !_.isEmpty( user )
cache = App.Store.get( 'navupdate_ticket_overview' )

View file

@ -45,7 +45,7 @@ class App.Auth
App.WebSocket.auth()
# rebuild navbar with new navbar items
App.Event.trigger 'navrebuild'
App.Event.trigger 'ajax:auth'
return false;
@ -69,10 +69,7 @@ class App.Auth
App.Collection.reset( type: key, data: value )
# rebuild navbar with new navbar items
App.Event.trigger 'navrebuild', data.session
# rebuild navbar with updated ticket count of overviews
App.Event.trigger 'navupdate_remote'
App.Event.trigger 'ajax:auth', data.session
error: (xhr, statusText, error) =>
console.log 'loginCheck:error'#, error, statusText, xhr.statusCode

View file

@ -19,10 +19,15 @@ class App.WebSocket
@connect()
_instance.auth(args)
@_spool: ->
_instance.spool()
# The actual Singleton class
class _Singleton extends App.Controller
queue: []
supported: true
supported: true
lastSpoolMessage: undefined
connectionEstablished: false
constructor: (@args) ->
@ -30,6 +35,11 @@ class _Singleton extends App.Controller
App.Event.bind 'ws:send', (data) =>
@send(data)
# get spool messages after successful ws login
App.Event.bind( 'ws:login', (data) =>
@spool()
)
# inital connect
@connect()
@ -58,6 +68,23 @@ class _Singleton extends App.Controller
}
@send(data)
spool: =>
# build data to send to server
data =
action: 'spool'
if @lastSpoolMessage
data['timestamp'] = @lastSpoolMessage
@log 'spool', data
# ask for spool messages
App.Event.trigger(
'ws:send'
data
)
# set timestamp to get spool messages later
@lastSpoolMessage = Math.round( +new Date()/1000 )
close: =>
return if !@supported
@ -103,6 +130,8 @@ class _Singleton extends App.Controller
@ws.onopen = =>
console.log( 'onopen' )
@connectionEstablished = true
# close error message show up (because try so connect again) if exists
@clearDelay('websocket-no-connection-try-reconnect')
if @error
@ -149,6 +178,11 @@ class _Singleton extends App.Controller
@ws.onclose = (e) =>
console.log( 'onclose', e )
# set timestamp to get spool messages later
if @connectionEstablished
@lastSpoolMessage = Math.round( +new Date()/1000 )
@connectionEstablished = false
# show error message, first try to reconnect
if !@error
message = =>

View file

@ -330,3 +330,8 @@ footer {
text-shadow: 0 1px 0 #fff;
opacity: 0.9;
}
.well-demand {
padding: 8px 15px 0px 15px
}
}

View file

@ -3,6 +3,7 @@
<div id="navigation"></div>
<div id="notify"></div>
<div id="content"></div>
<div id="chat"></div>
</div>
<div class="container">

View file

@ -12,6 +12,14 @@ module Session
user = { :id => session['id'] }
file.puts Marshal.dump(user)
}
# send update to browser
if session['id']
self.transaction( client_id, {
:event => 'ws:login',
:data => { :success => true },
})
end
end
def self.get( client_id )

View file

@ -44,6 +44,7 @@ puts "Starting websocket server on #{ @options[:b] }:#{ @options[:p] } (secure:#
#puts options.inspect
@clients = {}
@spool = []
EventMachine.run {
EventMachine::WebSocket.start( :host => @options[:b], :port => @options[:p], :secure => @options[:s], :tls_options => tls_options ) do |ws|
@ -89,6 +90,27 @@ EventMachine.run {
# check if connection already exists
next if !@clients[client_id]
# spool messages for new connects
if data['spool']
meta = {
:msg => msg,
:timestamp => Time.now.to_i,
}
@spool.push meta
end
# get spool messages
if data['action'] == 'spool'
@spool.each { |message|
puts message.inspect
puts data['timestamp']
if !data['timestamp'] || data['timestamp'] < message[:timestamp]
puts "send spool msg to #{client_id} #{ message[:msg] }"
@clients[client_id][:websocket].send( "[#{ message[:msg] }]" )
end
}
end
# get session
if data['action'] == 'login'
@clients[client_id][:session] = data['session']
@ -103,6 +125,7 @@ EventMachine.run {
elsif data['action'] == 'broadcast'
@clients.each { |local_client_id, local_client|
if local_client_id != client_id
puts "send broadcast to #{local_client_id} #{msg}"
local_client[:websocket].send( "[#{msg}]" )
end
}
@ -137,7 +160,7 @@ EventMachine.run {
}
}
EventMachine.add_periodic_timer(0.2) {
EventMachine.add_periodic_timer(0.4) {
next if @clients.size == 0
log 'debug', "checking for data..."
@clients.each { |client_id, client|
@ -164,7 +187,7 @@ EventMachine.run {
end
}
}
def log( level, data, client_id = '-' )
if !@options[:d]
return if level == 'debug'