message this user

Name

chat-server

Global

#import peer
#import parallel
#import jquery

function savemessages(msgs) {
 $.post('/skey/set/chat-server:msgs',JSON.stringify(msgs),()=>{});
}
function getmessages(cb) {
 $.post('/skey/get/chat-server:msgs',(msgs)=>{
  cb(JSON.parse(msgs||'[]'));
 });
}

function getchatserverdependencies(cb) {
 parallel([getjquery],cb);
}

function initiate_ui() {
 $('body').append($('<table>').append($('<tbody>')));
}

function startChatServer (dorendermessages) {
 function addmessagetorender(msg) {
  //Delete, user, message
  var tr = $('<tr>');
  var del = $('<td>').text('delete').attr('style','cursor:pointer');
  var user= $('<td>').text(msg.user);
  var msgtd = $('<td>').text(msg.msg);
  tr.append(del,user,msgtd);
  $('tbody').append(tr);
  $('tbody').children().slice(0,-35).remove();
  del.click(()=>{
   tr.remove();
   msgs = msgs.filter(i=>{
    console.log(msg.msg,i.msg,msg.user,i.user);
    return !(i.msg == msg.msg && i.user == msg.user); 
   });
   savemessages(msgs);
  });
 }
 console.log('starting');
 var serverstart = Date.now();
 var user2conn = {};
 var msgs = [];
 var userpostlog = [];
 window.user2conn = user2conn;
 getchatserverdependencies(()=>{
  if(dorendermessages) {
   initiate_ui();
  }
  getmessages(oldmsgs=>{
   msgs = oldmsgs;
   if(dorendermessages) {
    msgs.forEach(addmessagetorender);
   }
  });
  registernewpeer(function attachpeerlisteners(peer) {
   window.peer = peer;
   peer.on('error',error=>{
    console.log('peer error:',error);
   });
   peer.on('close',()=>{
    console.log('peer was closed');
    registernewpeer(attachpeerlisteners);
   });
   peer.on('disconnect',()=>{
    console.log('peer was disconnected');
    peer.reconnect();
   });
   peer.on('connection',conn=>{
    var connuser='test';
    var registered=false;
    console.log('new connection');
    conn.on('error',error=>{
     console.log('conn error:',error);
    });
    conn.on('close',()=>{
     delete user2conn[user];
     Object.keys(user2conn).forEach(outuser=>{
      user2conn[outuser].send(JSON.stringify({cmd:'left',user:user}));
     });
    });
    conn.on('data',data=>{
     data = JSON.parse(data);
     console.log(user,data);
     if(data.cmd=='register') {
      console.log('peer is registering',data.user)
      $.post('/peer/getid/'+data.user,resp=>{
       console.log('test',data.user,resp,conn.peer);
       //If peer is who they say they are.
       if(resp==conn.peer || resp==peer.id) {
        console.log('setting user',data.user);
        connuser=data.user;
        registered=true;
        Object.keys(user2conn).forEach(outuser=>{
         user2conn[outuser].send(JSON.stringify({cmd:'joined',user:connuser}));
        });
        user2conn[connuser]=conn;
        conn.send(JSON.stringify({cmd:'registered',registered:true}));
        conn.send(JSON.stringify({cmd:'posts',msg:msgs}));
        conn.send(JSON.stringify({cmd:'peerlist',msg:Object.keys(user2conn)}));
       }
      });
     }
     else if(data.cmd=='post') {
      if(!registered) { return console.log('user is not registered yet',data); }
      msgs.push(data);
      msgs=msgs.slice(-30);
      userpostlog.push({user:user,time:Date.now()});
      if(dorendermessages) {
       addmessagetorender(data);
      }
      Object.keys(user2conn).forEach(outuser=>{
       if(outuser==connuser) { return; }
       console.log('duplicating message from',connuser,data.user);
       user2conn[outuser].send(JSON.stringify({cmd:'post',user:connuser,msg:data.msg}));
      });
      savemessages(msgs);
     }
     else if(data.cmd=='logout') {
      conn.disconnect();
      delete user2conn[user];
      Object.keys(user2conn).forEach(outuser=>{
       user2conn[outuser].send(JSON.stringify({cmd:'left',user:user}));
      });
     }
    });
   });
  });
 });
 setInterval(()=>{
  //Log unique in 30 minutes.
  var now = Date.now();
  var thirtyminago = now-1000*60*30;
  if(thirtyminago < serverstart) {
   return;  //We don't want to clutter our data when the server hasn't run for 30 minutes.
  }
  userpostlog = userpostlog.filter(i=>{
   return i.time > thirtyminago;
  });
  var uniqusers = {};
  userpostlog.forEach(i=>{
   uniqusers[i.user]=true;
  });
  console.log('::traffic: ',Object.keys(uniqusers).length);
 },1000*60);
}

Init

console.log('We run code');
var dorender = true;
startChatServer(dorender);

Build

chat-server