0

Working on a chat server, I need to receive json via gen_tcp in erlang.

One way is to send a 4byte int header which is a good idea so i can also reject messages from clients if they exceed the max length but add complexity on client side. Another way is to read line, should work too for json if i am not wrong.

Third idea is to read json using depth tracking (counting '{' maybe?) That way i can also set max message length and make client code less complex. How can i do it specially with erlang i.e. check number of square brackets opened and keep receiving till last closes? or if its even a good idea? How does xmpp and other messaging protocols handle this problem?

asim
  • 533
  • 6
  • 17
  • Is your client sending data over a socket using erlang? – 7stud Feb 03 '19 at 03:41
  • No, could be anything, android, ios, windows, web – asim Feb 03 '19 at 06:30
  • Then it seems like there are two options: 1) A message ends when other side closes the socket (which sends an eof signal to the other side of the socket). 2) Both sides have to agree on some protocol that will signal the end of a message, e.g. byte headers. – 7stud Feb 03 '19 at 18:52
  • 1, not a good idea. 2, done things like that in the past, not satisfied. – asim Feb 03 '19 at 18:54

1 Answers1

2

Another way is to read line, should work too for json if i am not wrong.

Any key or value in json can contain a newline, and if your read protocol is: "Stop reading when a newline character is read from the socket.", you will not read the whole json if any key or value in the json has a newline character in it.

Third idea is to read json using depth tracking (counting '{' maybe?)

Ugh. Too complex. And json can start with a [ as well. And, a key or value could contain a ] or a } too.

The bottom line is: you need to decide on what should mark the end of a sent message. You could choose some relatively unique string like: --*456?END OF MESSAGE!123**--, but once again a key or value in the json could possibly contain that string--and that is why byte headers are used. You should be able to make an informed choice on how you want to proceed after reading this.

7stud
  • 46,922
  • 14
  • 101
  • 127
  • Got it but how does something like xmpp does that? any idea? – asim Feb 03 '19 at 08:03
  • @user10844401, Search the [ejabberd source code](https://github.com/processone/ejabberd) for "packet", and look around. – 7stud Feb 03 '19 at 18:47
  • I already did and it seems to be receiving all data in raw mode while listener seems to be passive – asim Feb 03 '19 at 18:50
  • 1
    See jsx's stream feature. Also Ejabberd uses fast_xml's stream feature which manages max_length for each XML in stream. – Pouriya Feb 03 '19 at 20:16
  • Comment from Pouriya along with the above answer should be the right answer hence marking it as accepted answer, thankyou very much. – asim Feb 05 '19 at 10:23