The ultra secure chat
Tags: opensource, go, security, discuss
Published: 2020-12-03 16:54:07

## I know what you're doing
Have you ever wondered who else has got the ability to read through your chat messages? Who can see your naughty pictures and the unfunny memes you've sent to your friends?
Well this shouldn't shock you that much since you're in the DEV community but you are not the only one.

Especially if you use services like WhatsApp, Instagram or any other service powered by a company.

## The Problem
Although knowing all of this, I don't know anybody who ever dared switching to a more secure messenger (at least nobody who had nothing to hide). All these big messengers are way to comfortable. You just install any app, the contacts will be auto-imported to the messenger and you're good to go and you can send messages to your friends, family (including grand parents) so on and so forth.

Almost everybody on this earth is using an messenger you can contact him over, this comfort just makes switching an disaster. And by this blog post nothing will change, since you give away much more comfort by using this than you're doing by using Signal or Telegram).

## So... What is this?
This is a brief overview of my [latest chat concept named asfaleia][asfaleia] (Greek word for security). It does not store any data on the server and the clients only authenticate through public and their correlating private keys. The project itself (by RoyalZSoftware) isn't finished yet. I mean it's in the rapid development phase and just consists of two commits. So if you've understand these concepts and want to work on this project, feel free to do so
[github.com/royalzsoftware/asfaleia][asfaleia]

This article will cover the basic concept of my chat idea with some deeper specification concerning the packets. There are more than a few possible enhancements, especially on the network part (since I'm a noob at this topic), but let's dive in.

## General
The server used by asfaleia is a simple TCP server written in go. Just a few lines by now.
```go
l, err := net.Listen("tcp4", "0.0.0.0:3308")
if err != nil {
    fmt.Println(err)
    return
}
defer l.Close()
for {
    c, err := l.Accept()

    if err != nil {
        fmt.Println(err)
        return
    }
    go handleConnection(c)
}
```
Where the `handleConnection(c)` function is invoked inside a new thread to handle each client simultaneously.

Currently not developed but planned is an `Message` struct containing an message, an [receiver](#receiver) and an [sender](#sender).

## Communication itself and Contacts?
### Authentication
The protocol uses ssh keypairs to verify identities. In order to tell the server now that you are this "public Key" the client sends an AUTH-Packet with his public key to the server.

The server then generates an random string which will then be encrypted with the sent public key.

After this procedure the server sends back an ANSWER-Packet containing the encrypted message with an handle, which in plain would look like this:

```
# Client sends following
0;MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQC1DGPUSPqPJdcWvdBNM5ymAQlKIXbLMa3X4D0JaBKKqv47w4ii3sLw2lckEHk+8LGyBNkbQN0aaVxWeuo4R7IsBMXVpJgvf/iQImRm5b9HIxkAYi5PqYGcHKBqiuzuHmpPlGYdGpM+hK5EeWiDj/sRVcP42KyYzGmd6ExbqaWMewIDAQAB
# Server sends back following
1;1238013;aMbZ55lweKk7+grkGQhzZHkl2Jt6cjKxzmnQ+gq6ydsYzs1830JqNgcZzbTsHI9hSOvuii6AXwF0WY6WnHnKsANDdC+mTDcvz51D2eiwt27xEK5N2toiJ0bE4SJcf25vtTi9hKH3D/xVpdEzXcH3vMNiB4UKl410eF33PijI4Ws=
```
Where at the both packets `0` or `1` stands for the `packet identifier`. In the server-response example beginning with `1` the second argument after a `;` is the handle that the client needs to pass in the AuthVerifyPacket he will later send. The last field is the encrypted message (in this example it's just a plain `Hello World`) base64 encoded.

Upon receiving this information the client now sends an AuthVerifyPacket
```
2;12380138;Hello World
```

If this works the client receives an jwt auth token verifying his identity which he will later needs to pass to every request.

### Sender
But how could senders and receivers be anonymous within a chatroom? Technically they can, but sure enough it depends on the way they are using these program. You can't be anonymous if you make yourself identifiable with any chat message.

The protocol itself uses ssh keypairs to verify their identity. Conversation partners can now use the ssh public key of the receiver, encrypt their message with it and send a packet to the server containing:

- The public key of the receiver
- The (with the public key) encrypted message

### Receiver
The receiver can send an GET-Packet which returns all the `Message[]` messages stored in an two-dimensional array. Once the server has finished sending the messages those are removed from the array so nobody ever can find out what was sent.

### Drawbacks
Although it's safe that none data is save to the disk, this also means that there isn't a chat history you can scroll through or any other thing related.

Furthermore you can't just write somebody with an contact, you need his full public key which you need to transfer.

## Conclusion
Well although this won't be used for mobile applications there may be a use for hidden services. If you like this approach and want to help developing this feel free to do so on [GitHub][asfaleia].

*How much do you value your privacy?* **Leave a comment!**

[asfaleia]: https://github.com/royalzsoftware/asfaleia