Building an end-to-end encryption framework in Swift

Ricardo Santos
5 min readJan 19, 2021
2016 @ https://tinyurl.com/y28qzkz8

Intro

Security can be a major concern for companies and developers building applications, especially in the medical field where data breaches are severely penalized. This is where end-to-end encryption comes into play.

A couple of days ago I read this article that inspired me to do a Swift library with utilities around Apple CryptoKit. When the time came to test it against using a real server, I end up adapting the library to an end-to-end (client-server-client) encryption tool.

The article is about my path doing that library, and also how I built client app and web server to test the concept.Before we start, I want to give you a quick intro about how 2 entities can “safely” agree on a (secret) key exchange that will latter be used to encrypt all messages, the Diffie-Helman key exchange algorithm.

I — Diffie-Helman key exchange algorithm.

Before we start, just quick intro about how 2 entities can “safely” agree on a (secret) key exchange that will latter be used to encrypt all messages, the Diffie-Helman key exchange algorithm.

https://en.wikipedia.org/wiki/Diffie%E2%80%93Hellman_key_exchange

There are 3 concepts to keep in mind:

  • Salt : (common paint) is the same and is know only by Alice and Bob, and can be seen as starting “password” between Alice and Bob.
  • Public Key : Both Alice and Bob have one and there is no problem if more entities know then.
  • Private key : (Secret colours) Both Alice and Bob have one, and only Alice know his Private key and only Bob know his Private key either.
AliceSecret = Salt + Alice.PrivateKey + Bob.PublicKey
BobSecret = Salt + Bob.PrivateKey + Alice.PublicKey

AliceSecret and BobSecret should share the same Symmetric key value that will be used to encrypt the messages. used to encrypt the messages.

II — Building

Building the basic operations

First tests

  • Alice (our sender entity) and Bob (receiver entity), both with Public and Private keys.
  • A Salt (common paint).
  • A secret message “my secret”.

We can define all (using Swift) and RJSP_Security as follow:

And we can simulate the:

  • Symmetric key exchange (line 4 and 8).
  • Encryption latter (line 5) by Alice using the common Salt, her Private Key a Bob Public Key.
  • Decryption by Bob (line 9) using the common Salt, his Private Key a Alice Public Key.

III — Testing on real App-Server-App use case

GIF at : https://github.com/ricardopsantos/RJSP_Security/blob/master/_Documents/preview.1.gif

Step 1: The app (client) sends its Public key to the server (in the request body). It also sends its userID (in the request header).

The request definition is below:

The request execution is below: (btw, how are your Combine skills?)

Step 2: The server stores the USER_ID and the user’s Public key (for future secure communication) and returns the server Public key to the client app.

Step 3: The client app receives the server Public key, and then with its (client) Private key executes a secure/encrypted request to the server.

The request definition is below:

Step 4: The server receives the encrypted request, and decrypts it using the client Public key (stored on step 1) and its (server) Private key. After decrypting the message, the server just returns it as a “proof” of success.

IV — Materials

  • All the code used on this articles, as for the sample client app and server app, can be found at RJSP_Security
  • If you are not familiar with Vapor (server app) and you want to learn more, this article will help you for sure.

V — Final notes

VI — Article review by

--

--